//------------------------------------------------------------------------------
// Copyright (c) 2005, 2006 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 implementation
//------------------------------------------------------------------------------
package org.eclipse.epf.library.configuration;

import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

import org.eclipse.emf.ecore.EStructuralFeature;
import org.eclipse.epf.uma.MethodElement;
import org.eclipse.epf.uma.VariabilityElement;
import org.eclipse.epf.uma.ecore.util.OppositeFeature;

/**
 * realized feature value for a toMany opposite feature
 * 
 * @author Jinhua Xi
 * @since 1.0
 *
 */
public class ToManyOppositeFeatureValue extends ToManyFeatureValue {
	
	/**
	 * @see construct a feature value object for to-many opposite feature
	 * 
	 * @param element
	 * @param feature
	 * @param realizer
	 */
	public ToManyOppositeFeatureValue(MethodElement element, OppositeFeature feature, ElementRealizer realizer) {
		super(element, null, feature, realizer);
	}

	

	/**
	 * @see org.eclipse.epf.library.configuration.ToManyFeatureValue#add(VariabilityElement, Object)
	 */
	public void add(VariabilityElement owner, Object value) {
		
		// work around for opposite feature value that still return a single value instead of a list
		if ( value instanceof MethodElement ) {
			ArrayList v = new ArrayList();
			v.add(value);
			value = v;
		}
		
		if ( !(value instanceof List) ) {	
			return;
		}
			
		for (Iterator it = ((List) value).iterator(); it.hasNext();) {
			MethodElement e = (MethodElement) it.next();

			// Replace does not completely remove
			// outgoing associations
			// if the opposite feature value has replacer in the
			// configuration
			// it's outgoing associations (i.e., this element) will be
			// replaced by the replacing element
			// as a result, the opposite feature value should drop the
			// replaced element
			//
			// for example, R1 -> responsible for A1, R2 responsible for
			// A2
			// if R2 replaces R1, then R2 still responsible for A2
			// but A1 does not have a responsible role (not R2)
			// so for A1's responsible role opposite feature,
			// the value R1 should be dropped instead of realize to R2
			// Jinhua Xi, 10/27/2005
			VariabilityElement replacer = null;
			if ( e instanceof VariabilityElement ) {
				replacer = ConfigurationHelper.getReplacer((VariabilityElement) e, realizer.getConfiguration());
			}
			boolean isValueReplaced = (replacer != null);

			boolean keep = !isValueReplaced;
			if ( isValueReplaced && 
					(ConfigurationHelper.isExtendReplacer(replacer) 
					|| ElementRealizer.isExtendReplaceEnabled()) ) {
				// if the value is replaced, but the out going feature is inherited by the replacer
				// then we should keep this value, so we need to calculate the feature value 
				// of the replacer
				OppositeFeature of = (OppositeFeature)feature;
				EStructuralFeature f = of.getTargetFeature();
				if ( f.isMany() ) {
					List items = ConfigurationHelper.calc0nFeatureValue(replacer, f, realizer);
					keep = items.contains(owner);
				} else {
					MethodElement item = ConfigurationHelper.calc01FeatureValue(replacer, f, realizer);
					keep = (item == owner);
				}
			}
			
			// if the value's feature to this element is to-one, 
			// then this value's feature value should be the element,
			// otherwise drop the value
			// for example, 
			// T1 -> R1 (primary performaer)
			// T2 -> R2
			// T2 contributes to T1
			// since T1 already has R1, so R2 is droped
			// so when calculating R2's performing tasks, T1 should not be included
			if ( keep ) {
				MethodElement ve = ConfigurationHelper.getCalculatedElement(e, realizer);
				if ( ve != null ) {
					OppositeFeature of = (OppositeFeature)feature;
					
					// check if this is a to-one feature, currently only Task->Primary Role and TD -> Primary RD
					EStructuralFeature f = ConfigurationHelper.get01Feature(of);
					if ( f != null ) {
						MethodElement item = ConfigurationHelper.calc01FeatureValue(ve, f, realizer);
						
						// if the value element's to-one feature value item is not the current element, 
						// then the element's opposite feature value should not contain this value.
						// say, the value element is a task and the current element is a role,
						// then if the task's primary performer (item above) is not this role (the current element), 
						// then the role's performing tasks (the opposite feature value) 
						// should not contain this task (the value, ve above)
						if ( item != element) {
							keep = false;
						}
					}
				}
			}
			
			
			if ( keep ) {
					
				MethodElement ce = ConfigurationHelper.getCalculatedElement(e, realizer);

				// calculated element can be null if it can't show
				if (ce != null && !values.contains(ce)) {
					values.add(ce);
				}
			}
		}	
	}
	
}
