Aptana Journal #10: Menampilkan Parameter Di Content Assist


Walaupun berhasil menampilkan ‘polymorphism‘ di content assist, seluruh nama method yang muncul selalu dengan nama yang sama.  Hal ini terkadang bisa sangat membingungkan.  Oleh sebab itu, saya ingin melakukan perubahan dimana nama method yang muncul di content assist juga menyertakan parameter.

Untuk itu, saya perlu mengubah method addProposal(Set<ICompletionProposal>, PropertyElement, int, URI, String, String[] di class JSContentAssistProcessor dengan menambahkan bagian seperti berikut ini:

PropertyElementProposal proposal = null;
if (property instanceof FunctionElement) {
  FunctionElement function = (FunctionElement) property;
  String documentation = JSModelFormatter.CONTEXT_INFO.getDocumentation(function);
  ContextInformation contextInformation = new ContextInformation(function.getName(), documentation);

  String proposalValue = StringUtil.join(null, function.getName(), "(",
    StringUtil.join(", ", function.getParameterNames()), ")");
  proposal = new PropertyElementProposal(proposalvalue, function.getName()+"()", function.getName().length()+1,
    function, offset, replaceLength, projectURI, contextInformation);
}

Langkah berikutnya adalah mengubah constructor yang pernah saya tambahkan di PropertyElementProposal.  Saya akui bahwa perubahan ini bukan yang terbaik, karena saya hanya menambah tanpa berani mengubah karena takut merusak yang sudah ada.  Akibatnya, parameter constructor terlihat panjang seperti berikut ini:

public PropertyElementProposal(String displayString, String replacementString, int cursorPosition,
  PropertyElement property, int offset, int replaceLength, URI uri, ContextInformation contextInformation)
{
  super(replacementString, offset, replaceLength, cursorPosition, null, displayString, 
    contextInformation, null);
  this.property = property;
  this.uri = uri;
}

Perjuangan belum selesai sampai disini, karena urutan tampilnya content assist tiba-tiba jadi berantakan.  Saya perlu mencari tahu kenapa, dan akhirnya menemukan jawaban di method validate() milik CommonCompletionProposal. Sebagai informasi, class PropertyElementProposal adalah turunan dari CommonCompletionProposal, sehingga method validate() ini ikut dipanggil. Berikut adalah isi method validate():

public boolean validate(IDocument document, int offset, DocumentEvent event)
{
  if (offset < this._replacementOffset)
    return false;

  int overlapIndex = getDisplayString().length - _replacementString.length();
  overlapIndex = Math.max(0, overlapIndex);
  String endPortion = getDisplayString().substring(overlapIndex);
  boolean validated = isValidPrefix(getPrefix(document, offset), endPortion);

  if (validated && event!=null)
  {
     // ... kode program diabaikan
  }

  return validated;
}

Karena nilai _displayString sangat berbeda dengan nilai _replacementString, maka hasil variabel endPortion jadi aneh.  Tapi karena kode program ini bukan saya yang buat, saya tidak mengerti apa tujuan awalnya.

Lalu apa saya harus mengubah method validate() di CommonCompletionProposal?   Tidak, lebih baik saya men-override method validate() ini di PropertyElementProposal sehingga perubahan tidak berdampak CommonCompletionProposal yang lain.   Oleh sebab itu, saya menambahkan method berikut ini di PropertyElementProposal (yang isinya hampir sama seperti di CommonCompletionProposal:

@Override
public boolean validate(IDocument document, int offset, DocumentEvent event)
{
	if (offset < this._replacementOffset)
		return false;

	int posisiKurung = getDisplayString().indexOf('(');
	String propertyName = null;
	if (posisiKurung == -1) {
		propertyName = getDisplayString();
	} else {
		propertyName = getDisplayString().substring(0, getDisplayString().indexOf('('));
	}
	int overlapIndex = propertyName.length() - _replacementString.length();
	overlapIndex = Math.max(0, overlapIndex);
	String endPortion = getDisplayString().substring(overlapIndex);
	boolean validated = isValidPrefix(getPrefix(document, offset), endPortion);

	if (validated && event != null)
	{
		// make sure that we change the replacement length as the document content changes
		int delta = ((event.fText == null) ? 0 : event.fText.length()) - event.fLength;
		final int newLength = Math.max(_replacementLength + delta, 0);
		_replacementLength = newLength;
	}

	return validated;
}

Sekarang, content assist untuk method yang memiliki banyak variasi tidak akan terlihat membingungkan lagi karena sudah ada informasi parameter seperti yang terlihat pada gambar berikut ini:

Content Assist Dengan Informasi Parameter

Content Assist Dengan Informasi Parameter

Perihal Solid Snake
I'm nothing...

Apa komentar Anda?

Please log in using one of these methods to post your comment:

Logo WordPress.com

You are commenting using your WordPress.com account. Logout / Ubah )

Gambar Twitter

You are commenting using your Twitter account. Logout / Ubah )

Foto Facebook

You are commenting using your Facebook account. Logout / Ubah )

Foto Google+

You are commenting using your Google+ account. Logout / Ubah )

Connecting to %s

%d blogger menyukai ini: