/*******************************************************************************
 * Copyright (c) 2000, 2009 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 API and implementation
 *******************************************************************************/
package org.eclipse.jdt.core.tests.model;

import java.io.File;

import junit.framework.Test;

import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.Path;
import org.eclipse.jdt.core.JavaModelException;
import org.eclipse.jdt.core.tests.util.Util;
import org.eclipse.jdt.internal.compiler.impl.CompilerOptions;

/**
 * Test class for completion in Javadoc comment of a package declaration.
 */
public class JavadocPackageCompletionModelTest extends AbstractJavadocCompletionModelTest {

public JavadocPackageCompletionModelTest(String name) {
	super(name);
}

static {
//	TESTS_RANGE = new int[] { 11, 12 };
//	TESTS_NUMBERS = new int[] { 16 };
}
public static Test suite() {
	return buildModelTestSuite(JavadocPackageCompletionModelTest.class);
}

/* (non-Javadoc)
 * @see org.eclipse.jdt.core.tests.model.AbstractJavadocCompletionModelTest#setUp()
 */
protected void setUp() throws Exception {
	super.setUp();
	setUpProjectOptions(CompilerOptions.VERSION_1_5);
}

/*
 * Write files for self-hosting debug.
 */
protected void writeFiles(String[] sources) {

	// Get write directory path
	if (WRITE_DIR_FILE == null) return;

	// Get test name
	String testName = getName();
	int idx = testName.indexOf(" - ");
	if (idx > 0) {
		testName = testName.substring(idx+3);
	}
//	testName = "Test"+testName.substring(4);

	// Write sources to dir
	int length = sources.length / 2;
	for (int i=0; i<length; i++) {

		// Get pathes
		IPath filePath = new Path(sources[2*i]).removeFirstSegments(2); // remove project and source folder
		IPath dirPath = filePath.removeLastSegments(1);
		String fileDir = dirPath.toString();
		String typeName = filePath.removeFileExtension().lastSegment();
		if (i==0 && !typeName.equals("package-info")) {
			System.err.println("Invalid type name: '"+typeName+"' for test "+testName);
			continue;
		}

		// Create package dirs or delete dirs if already exist
		File packageDir = new File(WRITE_DIR_FILE, fileDir);
		if (!PACKAGE_FILES.contains(packageDir)) {
			if (packageDir.exists()) {
				PACKAGE_FILES.add(packageDir);
				Util.flushDirectoryContent(packageDir);
			} else if (packageDir.mkdirs()) {
				PACKAGE_FILES.add(packageDir);
			} else {
				System.err.println(packageDir+" does not exist and CANNOT be created!!!");
				continue;
			}
		}

		// Create test dir
		File testDir = new File(packageDir, testName);
		if (!testDir.exists() && !testDir.mkdir()) {
			System.err.println(testDir+" does not exist and CANNOT be created!!!");
			continue;
		}

		// Store names info
		String fullPathName = testDir.getAbsolutePath()+"\\"+typeName+".java";
		System.out.println("Write file "+fullPathName);
		String contents = null;
		if (i==0) { // package-info
			contents = sources[2*i+1].substring(0, sources[2*i+1].lastIndexOf(';'));
			contents += "."+testName+";\n";
		} else {
			int index = sources[2*i+1].indexOf(';');
			contents = sources[2*i+1].substring(0, index);
			contents += "."+testName;
			contents += sources[2*i+1].substring(index);
		}
		Util.writeToFile(contents, fullPathName);
	}
}

/**
 * @category Tests for tag names completion
 */
public void test001() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion on empty tag name:\n" +
		" * 	@\n" +
		" */\n" +
		"package javadoc;\n";
	completeInJavadoc("/Completion/src/javadoc/package-info.java", source, true, "@");
	assertResults(
		"author[JAVADOC_BLOCK_TAG]{@author, null, null, author, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"see[JAVADOC_BLOCK_TAG]{@see, null, null, see, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"version[JAVADOC_BLOCK_TAG]{@version, null, null, version, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"category[JAVADOC_BLOCK_TAG]{@category, null, null, category, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"since[JAVADOC_BLOCK_TAG]{@since, null, null, since, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"serial[JAVADOC_BLOCK_TAG]{@serial, null, null, serial, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"link[JAVADOC_INLINE_TAG]{{@link}, null, null, link, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"docRoot[JAVADOC_INLINE_TAG]{{@docRoot}, null, null, docRoot, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"linkplain[JAVADOC_INLINE_TAG]{{@linkplain}, null, null, linkplain, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"value[JAVADOC_INLINE_TAG]{{@value}, null, null, value, null, "+this.positions+JAVADOC_RELEVANCE+"}"
	);
}

public void test002() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion on impossible tag name:\n" +
		" * 	@deprec\n" +
		" */\n" +
		"package javadoc;\n";
	completeInJavadoc("/Completion/src/javadoc/package-info.java", source, true, "@deprec");
	assertResults("");
}

public void test003() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion on one letter:\n" +
		" * 	@a\n" +
		" */\n" +
		"package javadoc;\n";
	completeInJavadoc("/Completion/src/javadoc/package-info.java", source, true, "@a");
	assertResults(
		"author[JAVADOC_BLOCK_TAG]{@author, null, null, author, null, "+this.positions+JAVADOC_RELEVANCE+"}"
	);
}

public void test004() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion with several letters:\n" +
		" * 	@ser\n" +
		" */\n" +
		"package javadoc;\n";
	completeInJavadoc("/Completion/src/javadoc/package-info.java", source, true, "@ser");
	assertResults(
		"serial[JAVADOC_BLOCK_TAG]{@serial, null, null, serial, null, "+this.positions+JAVADOC_RELEVANCE+"}"
	);
}

public void test005() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion on full tag name:\n" +
		" * 	@since\n" +
		" */\n" +
		"package javadoc;\n";
	completeInJavadoc("/Completion/src/javadoc/package-info.java", source, true, "@since");
	assertResults(
		"since[JAVADOC_BLOCK_TAG]{@since, null, null, since, null, "+this.positions+JAVADOC_RELEVANCE+"}"
	);
}

public void test006() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion on @ inside text\n" +
		" */\n" +
		"package javadoc;\n";
	completeInJavadoc("/Completion/src/javadoc/package-info.java", source, true, "@");
	assertResults(
		"link[JAVADOC_INLINE_TAG]{{@link}, null, null, link, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"docRoot[JAVADOC_INLINE_TAG]{{@docRoot}, null, null, docRoot, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"linkplain[JAVADOC_INLINE_TAG]{{@linkplain}, null, null, linkplain, null, "+this.positions+JAVADOC_RELEVANCE+"}\n" +
		"value[JAVADOC_INLINE_TAG]{{@value}, null, null, value, null, "+this.positions+JAVADOC_RELEVANCE+"}"
	);
}

public void test007() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion on @d inside text\n" +
		" */\n" +
		"package javadoc;\n";
	completeInJavadoc("/Completion/src/javadoc/package-info.java", source, true, "@d");
	assertResults(
		"docRoot[JAVADOC_INLINE_TAG]{{@docRoot}, null, null, docRoot, null, "+this.positions+JAVADOC_RELEVANCE+"}"
	);
}

/**
 * @category Tests for types completion
 */
public void test010() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion after:\n" +
		" * 	@see Obj\n" +
		" */\n" +
		"package javadoc.tags;\n";
	completeInJavadoc("/Completion/src/javadoc/tags/package-info.java", source, true, "Obj");
	assertResults(
		"Object[TYPE_REF]{Object, java.lang, Ljava.lang.Object;, null, null, "+this.positions+R_DRICUNR+"}"
	);
}

public void test011() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion after:\n" +
		" * 	@see BasicTestRef\n" +
		" */\n" +
		"package javadoc.tags;\n";
	completeInJavadoc("/Completion/src/javadoc/tags/package-info.java", source, true, "BasicTestRef");
	assertResults(
		"BasicTestReferences[TYPE_REF]{org.eclipse.jdt.core.tests.BasicTestReferences, org.eclipse.jdt.core.tests, Lorg.eclipse.jdt.core.tests.BasicTestReferences;, null, null, "+this.positions+R_DRICNR+"}"
	);
}

public void test012() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion after:\n" +
		" * 	@see org.eclipse.jdt.core.tests.BasicTestRef\n" +
		" * 		Note: JDT-UI failed on this one\n" +
		" */\n" +
		"package javadoc.tags;\n";
	completeInJavadoc("/Completion/src/javadoc/tags/package-info.java", source, true, "org.eclipse.jdt.core.tests.BasicTestRef");
	assertResults(
		"BasicTestReferences[TYPE_REF]{org.eclipse.jdt.core.tests.BasicTestReferences, org.eclipse.jdt.core.tests, Lorg.eclipse.jdt.core.tests.BasicTestReferences;, null, null, "+this.positions+R_DRICQNR+"}"
	);
}

public void test013() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion after:\n" +
		" * 	@see java.la\n" +
		" * 		Note: JDT-UI fails on this one\n" +
		" */\n" +
		"package javadoc.tags;\n";
	completeInJavadoc("/Completion/src/javadoc/tags/package-info.java", source, true, "java.la");
	assertResults(
		"java.lang.annotation[PACKAGE_REF]{java.lang.annotation, java.lang.annotation, null, null, null, "+this.positions+R_DRICQNR+"}\n" +
		"java.lang[PACKAGE_REF]{java.lang, java.lang, null, null, null, "+this.positions+R_DRICQNR+"}"
	);
}

public void test014() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion after:\n" +
		" * 	@see pack.Bin\n" +
		" */\n" +
		"package javadoc.tags;\n";
	completeInJavadoc("/Completion/src/javadoc/tags/package-info.java", source, true, "pack.Bin");
	assertSortedResults(
		"Bin1[TYPE_REF]{pack.Bin1, pack, Lpack.Bin1;, null, null, "+this.positions+R_DRICQNR+"}\n" +
		"Bin2[TYPE_REF]{pack.Bin2, pack, Lpack.Bin2;, null, null, "+this.positions+R_DRICQNR+"}\n" +
		"Bin3[TYPE_REF]{pack.Bin3, pack, Lpack.Bin3;, null, null, "+this.positions+R_DRICQNR+"}\n" +
		"Bin4[TYPE_REF]{pack.Bin4, pack, Lpack.Bin4;, null, null, "+this.positions+R_DRICQNR+"}\n" +
		"Bin5[TYPE_REF]{pack.Bin5, pack, Lpack.Bin5;, null, null, "+this.positions+R_DRICQNR+"}"
	);
}

public void test015() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion after:\n" +
		" * 	@see I\n" +
		" * 		Note: completion list shoud not include base types.\n" +
		" */\n" +
		"package javadoc.tags;\n";
	completeInJavadoc("/Completion/src/javadoc/tags/package-info.java", source, true, "I");
	assertSortedResults(
		"IllegalMonitorStateException[TYPE_REF]{IllegalMonitorStateException, java.lang, Ljava.lang.IllegalMonitorStateException;, null, null, "+this.positions+R_DRICUNR+"}\n" + 
		"InterruptedException[TYPE_REF]{InterruptedException, java.lang, Ljava.lang.InterruptedException;, null, null, "+this.positions+R_DRICUNR+"}\n" + 
		"Inherited[TYPE_REF]{java.lang.annotation.Inherited, java.lang.annotation, Ljava.lang.annotation.Inherited;, null, null, "+this.positions+R_DRICNR+"}\n" + 
		"Iterator[TYPE_REF]{java.util.Iterator, java.util, Ljava.util.Iterator;, null, null, "+this.positions+R_DRICNR+"}"
	);
}

/**
 * @category Tests for fields completion
 */
public void test020() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion after:\n" +
		" * 	@see BasicTestReferences#FIE\n" +
		" */\n" +
		"package javadoc.tags;\n";
	completeInJavadoc("/Completion/src/javadoc/tags/package-info.java", source, true, "FIE");
	assertResults("");
}

public void test021() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion after:\n" +
		" * 	@see org.eclipse.jdt.core.tests.BasicTestReferences#FIE\n" +
		" */\n" +
		"package javadoc.tags;\n";
	completeInJavadoc("/Completion/src/javadoc/tags/package-info.java", source, true, "FIE");
	assertResults(
		"FIELD[FIELD_REF]{FIELD, Lorg.eclipse.jdt.core.tests.BasicTestReferences;, I, FIELD, null, "+this.positions+R_DRICNR+"}"
	);
}

public void test022() throws JavaModelException {
	String[] sources = {
		"/Completion/src/javadoc/tags/package-info.java",
			"/**\n" +
			" * Completion after:\n" +
			" * 	@see OtherTypes#bar\n" +
			" */\n" +
			"package javadoc.tags;\n",
		"/Completion/src/javadoc/tags/OtherTypes.java",
			"package javadoc.tags;\n" +
			"public class OtherTypes {\n" +
			"	int bar;\n" +
			"}"
	};
	completeInJavadoc(sources, true, "bar");
	assertResults(
		"bar[FIELD_REF]{bar, Ljavadoc.tags.OtherTypes;, I, bar, null, "+this.positions+R_DRICENNRNS+"}"
	);
}

public void test023() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion after:\n" +
		" * 	@see BasicTestReferences#\n" +
		" */\n" +
		"package javadoc.tags;\n";
	completeInJavadoc("/Completion/src/javadoc/tags/package-info.java", source, true, "#", 0); // empty token
	assertResults("");
}

public void test024() throws JavaModelException {
	String source =
		"/**\n" +
		" * Completion after:\n" +
		" * 	@see org.eclipse.jdt.core.tests.BasicTestReferences#\n" +
		" */\n" +
		"package javadoc.tags;\n";
	completeInJavadoc("/Completion/src/javadoc/tags/package-info.java", source, true, "#", 0); // empty token
	assertResults(
		"FIELD[FIELD_REF]{FIELD, Lorg.eclipse.jdt.core.tests.BasicTestReferences;, I, FIELD, null, "+this.positions+R_DRICNR+"}\n" +
		"wait[METHOD_REF]{wait(long, int), Ljava.lang.Object;, (JI)V, wait, (millis, nanos), "+this.positions+R_DRICNRNS+"}\n" +
		"wait[METHOD_REF]{wait(long), Ljava.lang.Object;, (J)V, wait, (millis), "+this.positions+R_DRICNRNS+"}\n" +
		"wait[METHOD_REF]{wait(), Ljava.lang.Object;, ()V, wait, null, "+this.positions+R_DRICNRNS+"}\n" +
		"toString[METHOD_REF]{toString(), Ljava.lang.Object;, ()Ljava.lang.String;, toString, null, "+this.positions+R_DRICNRNS+"}\n" +
		"notifyAll[METHOD_REF]{notifyAll(), Ljava.lang.Object;, ()V, notifyAll, null, "+this.positions+R_DRICNRNS+"}\n" +
		"notify[METHOD_REF]{notify(), Ljava.lang.Object;, ()V, notify, null, "+this.positions+R_DRICNRNS+"}\n" +
		"hashCode[METHOD_REF]{hashCode(), Ljava.lang.Object;, ()I, hashCode, null, "+this.positions+R_DRICNRNS+"}\n" +
		"getClass[METHOD_REF]{getClass(), Ljava.lang.Object;, ()Ljava.lang.Class<+Ljava.lang.Object;>;, getClass, null, "+this.positions+R_DRICNRNS+"}\n" +
		"finalize[METHOD_REF]{finalize(), Ljava.lang.Object;, ()V, finalize, null, "+this.positions+R_DRICNRNS+"}\n" +
		"equals[METHOD_REF]{equals(Object), Ljava.lang.Object;, (Ljava.lang.Object;)Z, equals, (obj), "+this.positions+R_DRICNRNS+"}\n" +
		"clone[METHOD_REF]{clone(), Ljava.lang.Object;, ()Ljava.lang.Object;, clone, null, "+this.positions+R_DRICNRNS+"}\n" +
		"BasicTestReferences[METHOD_REF<CONSTRUCTOR>]{BasicTestReferences(), Lorg.eclipse.jdt.core.tests.BasicTestReferences;, ()V, BasicTestReferences, null, "+this.positions+R_DRINR+"}"
	);
}

public void test025() throws JavaModelException {
	String[] sources = {
		"/Completion/src/javadoc/tags/package-info.java",
			"/**\n" +
			" * Completion after:\n" +
			" * 	@see OtherTypes#\n" +
			" */\n" +
			"package javadoc.tags;\n",
		"/Completion/src/javadoc/tags/OtherTypes.java",
			"package javadoc.tags;\n" +
			"public class OtherTypes {\n" +
			"	int foo;\n" +
			"	Object obj;\n" +
			"}"
	};
	completeInJavadoc(sources, true, "#", 0); // empty token
	assertResults(
		"obj[FIELD_REF]{obj, Ljavadoc.tags.OtherTypes;, Ljava.lang.Object;, obj, null, "+this.positions+R_DRICNRNS+"}\n" +
		"foo[FIELD_REF]{foo, Ljavadoc.tags.OtherTypes;, I, foo, null, "+this.positions+R_DRICNRNS+"}\n" +
		"wait[METHOD_REF]{wait(long, int), Ljava.lang.Object;, (JI)V, wait, (millis, nanos), "+this.positions+R_DRICNRNS+"}\n" +
		"wait[METHOD_REF]{wait(long), Ljava.lang.Object;, (J)V, wait, (millis), "+this.positions+R_DRICNRNS+"}\n" +
		"wait[METHOD_REF]{wait(), Ljava.lang.Object;, ()V, wait, null, "+this.positions+R_DRICNRNS+"}\n" +
		"toString[METHOD_REF]{toString(), Ljava.lang.Object;, ()Ljava.lang.String;, toString, null, "+this.positions+R_DRICNRNS+"}\n" +
		"notifyAll[METHOD_REF]{notifyAll(), Ljava.lang.Object;, ()V, notifyAll, null, "+this.positions+R_DRICNRNS+"}\n" +
		"notify[METHOD_REF]{notify(), Ljava.lang.Object;, ()V, notify, null, "+this.positions+R_DRICNRNS+"}\n" +
		"hashCode[METHOD_REF]{hashCode(), Ljava.lang.Object;, ()I, hashCode, null, "+this.positions+R_DRICNRNS+"}\n" +
		"getClass[METHOD_REF]{getClass(), Ljava.lang.Object;, ()Ljava.lang.Class<+Ljava.lang.Object;>;, getClass, null, "+this.positions+R_DRICNRNS+"}\n" +
		"finalize[METHOD_REF]{finalize(), Ljava.lang.Object;, ()V, finalize, null, "+this.positions+R_DRICNRNS+"}\n" +
		"equals[METHOD_REF]{equals(Object), Ljava.lang.Object;, (Ljava.lang.Object;)Z, equals, (obj), "+this.positions+R_DRICNRNS+"}\n" +
		"clone[METHOD_REF]{clone(), Ljava.lang.Object;, ()Ljava.lang.Object;, clone, null, "+this.positions+R_DRICNRNS+"}\n" +
		"OtherTypes[METHOD_REF<CONSTRUCTOR>]{OtherTypes(), Ljavadoc.tags.OtherTypes;, ()V, OtherTypes, null, "+this.positions+R_DRINR+"}"
	);
}

/**
 * @category Tests for methods completion
 */
public void test030() throws JavaModelException {
	String[] sources = {
		"/Completion/src/javadoc/tags/package-info.java",
			"/**\n" +
			" * Completion after:\n" +
			" * 	@see OtherTypes#meth\n" +
			" */\n" +
			"package javadoc.tags;",
		"/Completion/src/javadoc/tags/OtherTypes.java",
			"package javadoc.tags;\n" +
			"public class OtherTypes {\n" +
			"	void method() {};\n" +
			"}"
	};
	completeInJavadoc(sources, true, "meth");
	assertResults(
		"method[METHOD_REF]{method(), Ljavadoc.tags.OtherTypes;, ()V, method, null, "+this.positions+R_DRICNRNS+"}"
	);
}
public void test031() throws JavaModelException {
	String[] sources = {
		"/Completion/src/javadoc/tags/package-info.java",
			"/**\n" +
			" * Completion after:\n" +
			" * 	@see OtherTypes#\n" +
			" */\n" +
			"package javadoc.tags;",
		"/Completion/src/javadoc/tags/OtherTypes.java",
			"package javadoc.tags;\n" +
			"public class OtherTypes {\n" +
			"	void method() {};\n" +
			"	void foo() {};\n" +
			"}"
	};
	completeInJavadoc(sources, true, "#", 0); // empty token
	assertResults(
		"method[METHOD_REF]{method(), Ljavadoc.tags.OtherTypes;, ()V, method, null, "+this.positions+R_DRICNRNS+"}\n" +
		"foo[METHOD_REF]{foo(), Ljavadoc.tags.OtherTypes;, ()V, foo, null, "+this.positions+R_DRICNRNS+"}\n" +
		"wait[METHOD_REF]{wait(long, int), Ljava.lang.Object;, (JI)V, wait, (millis, nanos), "+this.positions+R_DRICNRNS+"}\n" +
		"wait[METHOD_REF]{wait(long), Ljava.lang.Object;, (J)V, wait, (millis), "+this.positions+R_DRICNRNS+"}\n" +
		"wait[METHOD_REF]{wait(), Ljava.lang.Object;, ()V, wait, null, "+this.positions+R_DRICNRNS+"}\n" +
		"toString[METHOD_REF]{toString(), Ljava.lang.Object;, ()Ljava.lang.String;, toString, null, "+this.positions+R_DRICNRNS+"}\n" +
		"notifyAll[METHOD_REF]{notifyAll(), Ljava.lang.Object;, ()V, notifyAll, null, "+this.positions+R_DRICNRNS+"}\n" +
		"notify[METHOD_REF]{notify(), Ljava.lang.Object;, ()V, notify, null, "+this.positions+R_DRICNRNS+"}\n" +
		"hashCode[METHOD_REF]{hashCode(), Ljava.lang.Object;, ()I, hashCode, null, "+this.positions+R_DRICNRNS+"}\n" +
		"getClass[METHOD_REF]{getClass(), Ljava.lang.Object;, ()Ljava.lang.Class<+Ljava.lang.Object;>;, getClass, null, "+this.positions+R_DRICNRNS+"}\n" +
		"finalize[METHOD_REF]{finalize(), Ljava.lang.Object;, ()V, finalize, null, "+this.positions+R_DRICNRNS+"}\n" +
		"equals[METHOD_REF]{equals(Object), Ljava.lang.Object;, (Ljava.lang.Object;)Z, equals, (obj), "+this.positions+R_DRICNRNS+"}\n" +
		"clone[METHOD_REF]{clone(), Ljava.lang.Object;, ()Ljava.lang.Object;, clone, null, "+this.positions+R_DRICNRNS+"}\n" +
		"OtherTypes[METHOD_REF<CONSTRUCTOR>]{OtherTypes(), Ljavadoc.tags.OtherTypes;, ()V, OtherTypes, null, "+this.positions+R_DRINR+"}"
	);
}

/**
 * @category Tests for constructors completion
 */
public void test040() throws JavaModelException {
	String[] sources = {
		"/Completion/src/javadoc/tags/package-info.java",
			"/**\n" +
			" * Completion after:\n" +
			" * 	@see OtherTypes#O\n" +
			" */\n" +
			"package javadoc.tags;\n",
		"/Completion/src/javadoc/tags/OtherTypes.java",
			"package javadoc.tags;\n" +
			"public class OtherTypes {\n" +
			"	void method() {};\n" +
			"	void foo() {};\n" +
			"}"
	};
	completeInJavadoc(sources, true, "O", 2); // 2nd occurence
	assertResults(
		"OtherTypes[METHOD_REF<CONSTRUCTOR>]{OtherTypes(), Ljavadoc.tags.OtherTypes;, ()V, OtherTypes, null, "+this.positions+R_DRINR+"}"
	);
}
public void test041() throws JavaModelException {
	String[] sources = {
		"/Completion/src/javadoc/tags/package-info.java",
			"/**\n" +
			" * Completion after:\n" +
			" * 	@see OtherTypes#O\n" +
			" */\n" +
			"package javadoc.tags;\n",
		"/Completion/src/javadoc/tags/OtherTypes.java",
			"package javadoc.tags;\n" +
			"public class OtherTypes {\n" +
			"	OtherTypes(int x) {};\n" +
			"	OtherTypes(Object obj, String str) {};\n" +
			"}"
	};
	completeInJavadoc(sources, true, "O", 2); // 2nd occurence
	assertResults(
		"OtherTypes[METHOD_REF<CONSTRUCTOR>]{OtherTypes(Object, String), Ljavadoc.tags.OtherTypes;, (Ljava.lang.Object;Ljava.lang.String;)V, OtherTypes, (obj, str), "+this.positions+R_DRINR+"}\n" +
		"OtherTypes[METHOD_REF<CONSTRUCTOR>]{OtherTypes(int), Ljavadoc.tags.OtherTypes;, (I)V, OtherTypes, (x), "+this.positions+R_DRINR+"}"
	);
}
}
