mirror of
https://github.com/JetBrains/intellij-sdk-code-samples.git
synced 2025-07-28 01:07:49 +08:00
references_and_resolve.md: Cleanup
This commit is contained in:
parent
f4fd8aed48
commit
16e10c0494
@ -2,12 +2,12 @@
|
|||||||
|
|
||||||
# References and Resolve
|
# References and Resolve
|
||||||
|
|
||||||
<link-summary>PSI references allow for resolving from a symbol usage to its declaration.</link-summary>
|
<link-summary>A PSI reference allows for resolving from a symbol usage to its declaration.</link-summary>
|
||||||
|
|
||||||
One of the most important and tricky parts in implementing a custom language PSI is resolving references.
|
One of the most important and tricky parts in implementing a custom language PSI is resolving references.
|
||||||
Resolving references gives users the ability to navigate from a PSI element usage (accessing a variable, calling a method, etc.) to the declaration of that element (the variable's definition, a method declaration, and so on).
|
Resolving references allows users to navigate from a PSI element usage (accessing a variable, calling a method, etc.) to the declaration of that element (the variable's definition, a method declaration, and so on).
|
||||||
|
|
||||||
This feature is needed in order to support the <ui-path>Navigate | Declaration or Usages</ui-path> action invoked by <shortcut>Ctrl/Cmd+B</shortcut> or clicking the mouse button while holding <shortcut>Ctrl/Cmd</shortcut> key, and it is a prerequisite for implementing the [Find Usages](find_usages.md) action, the [Rename Refactoring](rename_refactoring.md) and [Code Completion](code_completion.md).
|
This feature is required to support the <ui-path>Navigate | Declaration or Usages</ui-path> action invoked by <shortcut>Ctrl/Cmd+B</shortcut> or clicking the mouse button while holding <shortcut>Ctrl/Cmd</shortcut> key, and it is a prerequisite for implementing [finding usages](find_usages.md), [rename refactoring](rename_refactoring.md), and [code completion](code_completion.md).
|
||||||
|
|
||||||
The <ui-path>View | Quick Definition</ui-path> action is based on the same mechanism, so it becomes automatically available for all references that can be resolved by the language plugin.
|
The <ui-path>View | Quick Definition</ui-path> action is based on the same mechanism, so it becomes automatically available for all references that can be resolved by the language plugin.
|
||||||
To customize the exact document range to show in the popup (e.g., include "surrounding" code or comments), provide [`ImplementationTextSelectioner`](%gh-ic%/platform/lang-api/src/com/intellij/codeInsight/hint/ImplementationTextSelectioner.java) registered in `com.intellij.lang.implementationTextSelectioner` extension point.
|
To customize the exact document range to show in the popup (e.g., include "surrounding" code or comments), provide [`ImplementationTextSelectioner`](%gh-ic%/platform/lang-api/src/com/intellij/codeInsight/hint/ImplementationTextSelectioner.java) registered in `com.intellij.lang.implementationTextSelectioner` extension point.
|
||||||
@ -17,12 +17,13 @@ To customize the exact document range to show in the popup (e.g., include "surro
|
|||||||
All PSI elements which work as references (for which the <ui-path>Navigate | Declaration or Usages</ui-path> action applies) need to implement the
|
All PSI elements which work as references (for which the <ui-path>Navigate | Declaration or Usages</ui-path> action applies) need to implement the
|
||||||
[`PsiElement.getReference()`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiElement.java) method and to return a [`PsiReference`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiReference.java) implementation from that method.
|
[`PsiElement.getReference()`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiElement.java) method and to return a [`PsiReference`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiReference.java) implementation from that method.
|
||||||
The `PsiReference` can be implemented by the same class as `PsiElement`, or by a different class.
|
The `PsiReference` can be implemented by the same class as `PsiElement`, or by a different class.
|
||||||
An element can also contain multiple references (for example, a string literal can contain multiple substrings which are valid fully-qualified class names), in which case it can implement `PsiElement.getReferences()` and return the references as an array.
|
An element can also contain multiple references (for example, a string literal can contain multiple substrings which are valid fully qualified class names), in which case it can implement `PsiElement.getReferences()` and return the references as an array.
|
||||||
To optimize `PsiElement.getReferences()` performance, consider implementing [`HintedReferenceHost`](%gh-ic%/platform/core-api/src/com/intellij/psi/HintedReferenceHost.java) to provide additional hints.
|
To optimize `PsiElement.getReferences()` performance, consider implementing [`HintedReferenceHost`](%gh-ic%/platform/core-api/src/com/intellij/psi/HintedReferenceHost.java) to provide additional hints.
|
||||||
|
|
||||||
The primary method of the [`PsiReference`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiReference.java) interface is `resolve()`, which returns the element to which the reference points, or `null` if it was not possible to resolve the reference to a valid element (for example, should it point to an undefined class).
|
The primary method of the [`PsiReference`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiReference.java) interface is `resolve()`.
|
||||||
|
It returns the element to which the reference points, or `null` if it was not possible to resolve the reference to a valid element (for example, should it point to an undefined class).
|
||||||
The resolved element should implement the [`PsiNamedElement`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiNamedElement.java) interface.
|
The resolved element should implement the [`PsiNamedElement`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiNamedElement.java) interface.
|
||||||
In order to enable more advanced functionality, prefer implementing [`PsiNameIdentifierOwner`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiNameIdentifierOwner.java) over [`PsiNamedElement`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiNamedElement.java) where possible.
|
To enable more advanced functionality, prefer implementing [`PsiNameIdentifierOwner`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiNameIdentifierOwner.java) over [`PsiNamedElement`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiNamedElement.java) where possible.
|
||||||
|
|
||||||
> While the referencing element and the referenced element both may have a name, only the element which **introduces** the name (e.g., the definition `int x = 42`) needs to implement `PsiNamedElement`.
|
> While the referencing element and the referenced element both may have a name, only the element which **introduces** the name (e.g., the definition `int x = 42`) needs to implement `PsiNamedElement`.
|
||||||
> The referencing element at the point of usage (e.g., the `x` in the expression `x + 1`) should not implement `PsiNamedElement` since it does not _have_ a name.
|
> The referencing element at the point of usage (e.g., the `x` in the expression `x + 1`) should not implement `PsiNamedElement` since it does not _have_ a name.
|
||||||
@ -45,7 +46,7 @@ These interfaces have several extra complexities that are unnecessary for most c
|
|||||||
Still, they are required if the custom language can have references to Java code.
|
Still, they are required if the custom language can have references to Java code.
|
||||||
If Java interoperability is not required, the plugin can forgo the standard interfaces and provide its own, different implementation of resolve.
|
If Java interoperability is not required, the plugin can forgo the standard interfaces and provide its own, different implementation of resolve.
|
||||||
|
|
||||||
Please see also [](psi_performance.md#cache-results-of-heavy-computations).
|
See also [](psi_performance.md#cache-results-of-heavy-computations).
|
||||||
|
|
||||||
The implementation of resolve based on the standard helper classes contains the following components:
|
The implementation of resolve based on the standard helper classes contains the following components:
|
||||||
|
|
||||||
@ -63,7 +64,7 @@ The implementation of resolve based on the standard helper classes contains the
|
|||||||
|
|
||||||
## Resolving to Multiple Targets
|
## Resolving to Multiple Targets
|
||||||
|
|
||||||
An extension of the [`PsiReference`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiReference.java) interface, which allows a reference to resolve to multiple targets, is the [`PsiPolyVariantReference`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiPolyVariantReference.java) interface.
|
[`PsiPolyVariantReference`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiPolyVariantReference.java) is an extension of [`PsiReference`](%gh-ic%/platform/core-api/src/com/intellij/psi/PsiReference.java) and allows a reference to resolve to multiple targets.
|
||||||
The targets to which the reference resolves are returned from the `multiResolve()` method.
|
The targets to which the reference resolves are returned from the `multiResolve()` method.
|
||||||
The <ui-path>Navigate | Declaration or Usages</ui-path> action for such references allows the user to choose a navigation target in a popup.
|
The <ui-path>Navigate | Declaration or Usages</ui-path> action for such references allows the user to choose a navigation target in a popup.
|
||||||
The implementation of `multiResolve()` can be also based on [`PsiScopeProcessor`](%gh-ic%/platform/core-api/src/com/intellij/psi/scope/PsiScopeProcessor.java), and can collect all valid targets for the reference instead of stopping when the first valid target is found.
|
The implementation of `multiResolve()` can be also based on [`PsiScopeProcessor`](%gh-ic%/platform/core-api/src/com/intellij/psi/scope/PsiScopeProcessor.java), and can collect all valid targets for the reference instead of stopping when the first valid target is found.
|
||||||
|
Loading…
x
Reference in New Issue
Block a user