/*******************************************************************************
 * Copyright (c) 2000, 2004 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials 
 * are made available under the terms of the Common Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/cpl-v10.html
 * 
 * Contributors:
 *     IBM Corporation - initial API and implementation
 *******************************************************************************/
package org.eclipse.jdt.internal.core.jdom;

import java.util.Map;

import org.eclipse.jdt.core.JavaCore;
import org.eclipse.jdt.core.compiler.CharOperation;
import org.eclipse.jdt.core.compiler.IProblem;
import org.eclipse.jdt.core.jdom.*;
import org.eclipse.jdt.internal.compiler.ISourceElementRequestor;
import org.eclipse.jdt.internal.compiler.SourceElementParser;
import org.eclipse.jdt.internal.compiler.env.ICompilationUnit;
import org.eclipse.jdt.internal.compiler.impl.CompilerOptions;
import org.eclipse.jdt.internal.compiler.problem.DefaultProblemFactory;
/**
 * A DOM builder that uses the SourceElementParser
 * @deprecated The JDOM was made obsolete by the addition in 2.0 of the more
 * powerful, fine-grained DOM/AST API found in the 
 * org.eclipse.jdt.core.dom package.
 */
public class SimpleDOMBuilder extends AbstractDOMBuilder implements ISourceElementRequestor {

/**
 * Does nothing.
 */
public void acceptProblem(IProblem problem) {
	// nothing to do
}

public void acceptImport(int declarationStart, int declarationEnd, char[] name, boolean onDemand, int modifiers) {
	int[] sourceRange = {declarationStart, declarationEnd};
	String importName = new String(name);
	/** name is set to contain the '*' */
	if (onDemand) {
		importName+=".*"; //$NON-NLS-1$
	}
	fNode= new DOMImport(fDocument, sourceRange, importName, onDemand);
	addChild(fNode);	
}
public void acceptPackage(int declarationStart, int declarationEnd, char[] name) {
	int[] sourceRange= new int[] {declarationStart, declarationEnd};
	fNode= new DOMPackage(fDocument, sourceRange, CharOperation.charToString(name));
	addChild(fNode);	
}
/**
 * @see IDOMFactory#createCompilationUnit(String, String)
 */
public IDOMCompilationUnit createCompilationUnit(String sourceCode, String name) {
	return createCompilationUnit(sourceCode.toCharArray(), name.toCharArray());
}
/**
 * @see IDOMFactory#createCompilationUnit(String, String)
 */
public IDOMCompilationUnit createCompilationUnit(ICompilationUnit compilationUnit) {
	initializeBuild(compilationUnit.getContents(), true, true);
	getParser(JavaCore.getOptions()).parseCompilationUnit(compilationUnit, false/*diet parse*/);
	return super.createCompilationUnit(compilationUnit);
}
/**
 * Creates a new DOMMethod and inizializes.
 *
 * @param declarationStart - a source position corresponding to the first character 
 *		of this constructor declaration
 * @param modifiers - the modifiers for this constructor converted to a flag
 * @param returnType - the name of the return type
 * @param name - the name of this constructor
 * @param nameStart - a source position corresponding to the first character of the name
 * @param nameEnd - a source position corresponding to the last character of the name
 * @param parameterTypes - a list of parameter type names
 * @param parameterNames - a list of the names of the parameters
 * @param exceptionTypes - a list of the exception types
 */
protected void enterAbstractMethod(int declarationStart, int modifiers,
	char[] returnType, char[] name, int nameStart, int nameEnd, char[][] parameterTypes,
	char[][] parameterNames, char[][] exceptionTypes, boolean isConstructor) {
		
	int[] sourceRange = {declarationStart, -1}; // will be fixed up on exit
	int[] nameRange = {nameStart, nameEnd};
	fNode = new DOMMethod(fDocument, sourceRange, CharOperation.charToString(name), nameRange, modifiers, 
		isConstructor, CharOperation.charToString(returnType),
		CharOperation.charArrayToStringArray(parameterTypes),
		CharOperation.charArrayToStringArray(parameterNames), 
		CharOperation.charArrayToStringArray(exceptionTypes));
	addChild(fNode);
	fStack.push(fNode);
}
/**
 */
public void enterClass(int declarationStart, int modifiers, char[] name, int nameStart, int nameEnd, char[] superclass, char[][] superinterfaces) {
	enterType(declarationStart, modifiers, name, nameStart, nameEnd, superclass,
		superinterfaces, true);
}
/**
 */
public void enterConstructor(int declarationStart, int modifiers, char[] name, int nameStart, int nameEnd, char[][] parameterTypes, char[][] parameterNames, char[][] exceptionTypes) {
	/* see 1FVIIQZ */
	String nameString = new String(fDocument, nameStart, nameEnd - nameStart);
	int openParenPosition = nameString.indexOf('(');
	if (openParenPosition > -1)
		nameEnd = nameStart + openParenPosition - 1;

	enterAbstractMethod(declarationStart, modifiers, 
		null, name, nameStart, nameEnd, parameterTypes,
		parameterNames, exceptionTypes,true);
}
/**
 */
public void enterField(int declarationStart, int modifiers, char[] type, char[] name, int nameStart, int nameEnd) {

	int[] sourceRange = {declarationStart, -1};
	int[] nameRange = {nameStart, nameEnd};
	boolean isSecondary= false;
	if (fNode instanceof DOMField) {
		isSecondary = declarationStart == fNode.fSourceRange[0];
	}
	fNode = new DOMField(fDocument, sourceRange, CharOperation.charToString(name), nameRange, 
		modifiers, CharOperation.charToString(type), isSecondary);
	addChild(fNode);
	fStack.push(fNode);
}
/**

 */
public void enterInitializer(int declarationSourceStart, int modifiers) {
	int[] sourceRange = {declarationSourceStart, -1};
	fNode = new DOMInitializer(fDocument, sourceRange, modifiers);
	addChild(fNode);
	fStack.push(fNode);
}
/**
 */
public void enterInterface(int declarationStart, int modifiers, char[] name, int nameStart, int nameEnd, char[][] superinterfaces) {
	enterType(declarationStart, modifiers, name, nameStart, nameEnd, null,
		superinterfaces, false);
}
/**
 */
public void enterMethod(int declarationStart, int modifiers, char[] returnType, char[] name, int nameStart, int nameEnd, char[][] parameterTypes, char[][] parameterNames, char[][] exceptionTypes) {
	enterAbstractMethod(declarationStart, modifiers, 
		returnType, name, nameStart, nameEnd, parameterTypes,
		parameterNames, exceptionTypes,false);
}
/**
 */
protected void enterType(int declarationStart, int modifiers, char[] name, 
	int nameStart, int nameEnd, char[] superclass, char[][] superinterfaces, boolean isClass) {
	if (fBuildingType) {
		int[] sourceRange = {declarationStart, -1}; // will be fixed in the exit
		int[] nameRange = new int[] {nameStart, nameEnd};
		fNode = new DOMType(fDocument, sourceRange, new String(name), nameRange,
			modifiers, CharOperation.charArrayToStringArray(superinterfaces), isClass);
		addChild(fNode);
		fStack.push(fNode);
	}
}
/**
 * Finishes the configuration of the class DOM object which
 * was created by a previous enterClass call.
 *
 * @see ISourceElementRequestor#exitClass(int)
 */
public void exitClass(int declarationEnd) {
	exitType(declarationEnd);
}
/**
 * Finishes the configuration of the method DOM object which
 * was created by a previous enterConstructor call.
 *
 * @see ISourceElementRequestor#exitConstructor(int)
 */
public void exitConstructor(int declarationEnd) {
	exitMember(declarationEnd);
}
/**
 */
public void exitField(int initializationStart, int declarationEnd, int declarationSourceEnd) {
	exitMember(declarationEnd);
}
/**
 */
public void exitInitializer(int declarationEnd) {
	exitMember(declarationEnd);
}
/**
 */
public void exitInterface(int declarationEnd) {
	exitType(declarationEnd);
}
/**
 * Finishes the configuration of the member.
 *
 * @param declarationEnd - a source position corresponding to the end of the method
 *		declaration.  This can include whitespace and comments following the closing bracket.
 */
protected void exitMember(int declarationEnd) {
	DOMMember m= (DOMMember) fStack.pop();
	m.setSourceRangeEnd(declarationEnd);
	fNode = m;
}
/**
 */
public void exitMethod(int declarationEnd) {
	exitMember(declarationEnd);
}
/**
 * @see AbstractDOMBuilder#exitType
 *
 * @param declarationEnd - a source position corresponding to the end of the class
 *		declaration.  This can include whitespace and comments following the closing bracket.
 */
protected void exitType(int declarationEnd) {
	exitType(declarationEnd, declarationEnd);
}
/**
 * Creates a new parser.
 */
protected SourceElementParser getParser(Map settings) {
	return new SourceElementParser(this, new DefaultProblemFactory(), new CompilerOptions(settings));
}
}
