/*******************************************************************************
* Copyright (c) 2013-2014 CWI
* 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:
*
* * Michael Steindorfer - Michael.Steindorfer@cwi.nl - CWI
*******************************************************************************/
package org.rascalmpl.value.impl;
import java.util.Iterator;
import org.rascalmpl.value.IAnnotatable;
import org.rascalmpl.value.IConstructor;
import org.rascalmpl.value.IList;
import org.rascalmpl.value.INode;
import org.rascalmpl.value.IValue;
import org.rascalmpl.value.IWithKeywordParameters;
import org.rascalmpl.value.exceptions.FactTypeUseException;
import org.rascalmpl.value.io.StandardTextWriter;
import org.rascalmpl.value.type.Type;
import org.rascalmpl.value.type.TypeStore;
import org.rascalmpl.value.visitors.IValueVisitor;
import io.usethesource.capsule.ImmutableMap;
public class AnnotatedConstructorFacade implements IConstructor {
protected final IConstructor content;
protected final ImmutableMap<String, IValue> annotations;
public AnnotatedConstructorFacade(final IConstructor content, final ImmutableMap<String, IValue> annotations) {
this.content = content;
this.annotations = annotations;
}
public <T, E extends Throwable> T accept(IValueVisitor<T, E> v) throws E {
return v.visitConstructor(this);
}
public Type getType() {
return content.getType();
}
public IValue get(int i) throws IndexOutOfBoundsException {
return content.get(i);
}
public Type getConstructorType() {
return content.getConstructorType();
}
public Type getUninstantiatedConstructorType() {
return content.getUninstantiatedConstructorType();
}
public IValue get(String label) {
return content.get(label);
}
public IConstructor set(String label, IValue newChild)
throws FactTypeUseException {
IConstructor newContent = content.set(label, newChild);
return new AnnotatedConstructorFacade(newContent, annotations); // TODO: introduce wrap() here as well
}
public int arity() {
return content.arity();
}
public boolean has(String label) {
return content.has(label);
}
public String toString() {
return StandardTextWriter.valueToString(this);
}
public IConstructor set(int index, IValue newChild)
throws FactTypeUseException {
IConstructor newContent = content.set(index, newChild);
return new AnnotatedConstructorFacade(newContent, annotations); // TODO: introduce wrap() here as well
}
public String getName() {
return content.getName();
}
public Iterable<IValue> getChildren() {
return content.getChildren();
}
public Iterator<IValue> iterator() {
return content.iterator();
}
public INode replace(int first, int second, int end, IList repl)
throws FactTypeUseException, IndexOutOfBoundsException {
return content.replace(first, second, end, repl);
}
public Type getChildrenTypes() {
return content.getChildrenTypes();
}
public boolean declaresAnnotation(TypeStore store, String label) {
return content.declaresAnnotation(store, label);
}
public boolean equals(Object o) {
if(o == this) return true;
if(o == null) return false;
if(o.getClass() == getClass()){
AnnotatedConstructorFacade other = (AnnotatedConstructorFacade) o;
return content.equals(other.content) &&
annotations.equals(other.annotations);
}
return false;
}
public boolean isEqual(IValue other) {
return content.isEqual(other);
}
@Override
public int hashCode() {
return content.hashCode();
}
@Override
public boolean isAnnotatable() {
return true;
}
@Override
public IAnnotatable<? extends IConstructor> asAnnotatable() {
return new AbstractDefaultAnnotatable<IConstructor>(content, annotations) {
@Override
protected IConstructor wrap(IConstructor content,
ImmutableMap<String, IValue> annotations) {
return annotations.isEmpty() ? content : new AnnotatedConstructorFacade(content, annotations);
}
};
}
@Override
public boolean mayHaveKeywordParameters() {
return false;
}
@Override
public IWithKeywordParameters<IConstructor> asWithKeywordParameters() {
throw new UnsupportedOperationException("can not add keyword parameters to a node which already has annotations");
}
}