All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.fife.rsta.ac.java.MethodInfoData Maven / Gradle / Ivy

/*
 * 03/21/2010
 *
 * Copyright (C) 2010 Robert Futrell
 * robert_futrell at users.sourceforge.net
 * http://fifesoft.com/rsyntaxtextarea
 *
 * This library is distributed under a modified BSD license.  See the included
 * RSTALanguageSupport.License.txt file for details.
 */
package org.fife.rsta.ac.java;

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

import org.fife.rsta.ac.java.MemberCompletion.Data;
import org.fife.rsta.ac.java.buildpath.SourceLocation;
import org.fife.rsta.ac.java.classreader.ClassFile;
import org.fife.rsta.ac.java.classreader.MethodInfo;
import org.fife.rsta.ac.java.classreader.Util;
import org.fife.rsta.ac.java.rjc.ast.CompilationUnit;
import org.fife.rsta.ac.java.rjc.ast.FormalParameter;
import org.fife.rsta.ac.java.rjc.ast.Member;
import org.fife.rsta.ac.java.rjc.ast.Method;
import org.fife.rsta.ac.java.rjc.ast.TypeDeclaration;


/**
 * Metadata about a method as read from a class file.  This class is used by
 * instances of {@link MethodCompletion}.
 *
 * @author Robert Futrell
 * @version 1.0
 */
class MethodInfoData implements Data {

	/**
	 * The parent completion provider.
	 */
	private SourceCompletionProvider provider;

	/**
	 * The actual metadata.
	 */
	private MethodInfo info;

	/**
	 * Cached method parameter names.
	 */
	private List paramNames;


	/**
	 * Constructor.
	 *
	 * @param info The method info.
	 * @param provider The parent completion provider.
	 */
	MethodInfoData(MethodInfo info, SourceCompletionProvider provider) {
		this.info = info;
		this.provider = provider;
	}


	@Override
	public String getEnclosingClassName(boolean fullyQualified) {
		return info.getClassFile().getClassName(fullyQualified);
	}


	@Override
	public String getIcon() {

		String key;
		int flags = info.getAccessFlags();

		if (Util.isDefault(flags)) {
			key = IconFactory.METHOD_DEFAULT_ICON;
		}
		else if (Util.isPrivate(flags)) {
			key = IconFactory.METHOD_PRIVATE_ICON;
		}
		else if (Util.isProtected(flags)) {
			key = IconFactory.METHOD_PROTECTED_ICON;
		}
		else if (Util.isPublic(flags)) {
			key = IconFactory.METHOD_PUBLIC_ICON;
		}
		else {
			key = IconFactory.METHOD_DEFAULT_ICON;
		}

		return key;

	}


	/**
	 * Scours the source in a location (zip file, directory), looking for a
	 * particular class's source.  If it is found, it is parsed, and the
	 * {@link Method} for this method (if any) is returned.
	 *
	 * @param loc The zip file, jar file, or directory to look in.
	 * @param cf The {@link ClassFile} representing the class of this method.
	 * @return The method, or null if it cannot be found, or an
	 *         IO error occurred.
	 */
	private Method getMethodFromSourceLoc(SourceLocation loc, ClassFile cf) {

		Method res = null;
		CompilationUnit cu = org.fife.rsta.ac.java.Util.
									getCompilationUnitFromDisk(loc, cf);

		// If the class's source was found and successfully parsed, look for
		// this method.
		if (cu!=null) {

			Iterator i = cu.getTypeDeclarationIterator();
			while (i.hasNext()) {

				TypeDeclaration td = i.next();
				String typeName = td.getName();

				// Avoid inner classes, etc.
				if (typeName.equals(cf.getClassName(false))) {

					// Get all overloads of this method with the number of
					// parameters we're looking for.  99% of the time, there
					// will only be 1, the method we're looking for.
					List contenders = null;
					for (int j=0; j(1); // Usually just 1
								}
								contenders.add(m2);
							}
						}
					}

					// We found some matches.
					if (contenders!=null) {

						// Common case - only 1 overload with the desired
						// number of parameters => it must be our method.
						if (contenders.size()==1) {
							res = contenders.get(0);
						}

						// More than 1 overload with the same number of
						// parameters... we decide which contender is the one
						// we're looking for by checking each of its
						// parameters' types and making sure they're correct.
						else {
							for (Method method : contenders) {
								boolean match = true;
								for (int p=0; pnull if it cannot be determined.
	 *
	 * @param index The index of the parameter.
	 * @return The name of the parameter, or null.
	 */
	public String getParameterName(int index) {

		// First, check whether the debugging attribute was enabled at
		// compilation, and the parameter name is embedded in the class file.
		// This method takes priority because it *likely* matches a name
		// specified in Javadoc, and is much faster for us to fetch (it's
		// already parsed).
		String name = info.getParameterName(index);

		// Otherwise...
		if (name==null) {

			// Next, check the attached source, if any (lazily parsed).
			if (paramNames==null) {

				paramNames = new ArrayList<>(1);
				int offs = 0;
				String rawSummary = getSummary();

				// If there's attached source with Javadoc for this method...
				if (rawSummary!=null && rawSummary.startsWith("/**")) {

					int nextParam;
					int summaryLen = rawSummary.length();

					while ((nextParam=rawSummary.indexOf("@param", offs))>-1) {
						int temp = nextParam + "@param".length() + 1;
						while (tempnull if the method has no javadoc,
	 *         the class's source was not found, or an IO error occurred.
	 */
	private String getSummaryFromSourceLoc(SourceLocation loc, ClassFile cf) {
		Method method = getMethodFromSourceLoc(loc, cf);
		return method!=null ? method.getDocComment() : null;
	}


	@Override
	public String getType() {
		return info.getReturnTypeString(false);
	}


	@Override
	public boolean isAbstract() {
		return info.isAbstract();
	}


	@Override
	public boolean isConstructor() {
		return info.isConstructor();
	}


	@Override
	public boolean isDeprecated() {
		return info.isDeprecated();
	}


	@Override
	public boolean isFinal() {
		return info.isFinal();
	}


	@Override
	public boolean isStatic() {
		return info.isStatic();
	}


}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy