idea: significant enhancements to ide experience

This commit is contained in:
2023-09-22 22:38:06 -07:00
parent 83c24843a3
commit c340cfb86d
46 changed files with 450 additions and 131 deletions

View File

@ -261,6 +261,7 @@ types:
parent: Expression parent: Expression
referencedElementValue: symbol referencedElementValue: symbol
referencedElementType: Node referencedElementType: Node
namedElementValue: symbol
values: values:
- name: symbol - name: symbol
type: Symbol type: Symbol

View File

@ -1,9 +1,9 @@
// GENERATED CODE FROM PORK AST CODEGEN // GENERATED CODE FROM PORK AST CODEGEN
package gay.pizza.pork.ast package gay.pizza.pork.ast
import kotlinx.serialization.Transient
import kotlinx.serialization.SerialName import kotlinx.serialization.SerialName
import kotlinx.serialization.Serializable import kotlinx.serialization.Serializable
import kotlinx.serialization.Transient
@Serializable @Serializable
@SerialName("node") @SerialName("node")

View File

@ -70,13 +70,15 @@ class AstPorkIdeaCodegen(pkg: String, outputDirectory: Path, world: AstWorld) :
), ),
inherits = mutableListOf("${baseType}(node)"), inherits = mutableListOf("${baseType}(node)"),
imports = mutableListOf( imports = mutableListOf(
"com.intellij.lang.ASTNode" "com.intellij.lang.ASTNode",
"gay.pizza.pork.idea.psi.PorkElementHelpers",
"javax.swing.Icon",
"com.intellij.navigation.ItemPresentation"
) )
) )
if (baseType == "PorkNamedElement") { if (baseType == "PorkNamedElement") {
kotlinClass.imports.add(0, "com.intellij.psi.PsiElement") kotlinClass.imports.add(0, "com.intellij.psi.PsiElement")
kotlinClass.imports.add("gay.pizza.pork.idea.psi.PorkElementHelpers")
val getNameFunction = KotlinFunction( val getNameFunction = KotlinFunction(
"getName", "getName",
overridden = true, overridden = true,
@ -111,7 +113,6 @@ class AstPorkIdeaCodegen(pkg: String, outputDirectory: Path, world: AstWorld) :
if (type.referencedElementValue != null && type.referencedElementType != null) { if (type.referencedElementValue != null && type.referencedElementType != null) {
kotlinClass.imports.add(0, "com.intellij.psi.PsiReference") kotlinClass.imports.add(0, "com.intellij.psi.PsiReference")
kotlinClass.imports.add("gay.pizza.pork.ast.NodeType") kotlinClass.imports.add("gay.pizza.pork.ast.NodeType")
kotlinClass.imports.add("gay.pizza.pork.idea.psi.PorkElementHelpers")
val getReferenceFunction = KotlinFunction( val getReferenceFunction = KotlinFunction(
"getReference", "getReference",
@ -123,6 +124,27 @@ class AstPorkIdeaCodegen(pkg: String, outputDirectory: Path, world: AstWorld) :
kotlinClass.functions.add(getReferenceFunction) kotlinClass.functions.add(getReferenceFunction)
} }
val getIconFunction = KotlinFunction(
"getIcon",
overridden = true,
returnType = "Icon?",
parameters = mutableListOf(
KotlinParameter("flags", "Int")
),
isImmediateExpression = true
)
getIconFunction.body.add("PorkElementHelpers.iconOf(this)")
kotlinClass.functions.add(getIconFunction)
val getPresentationFunction = KotlinFunction(
"getPresentation",
overridden = true,
returnType = "ItemPresentation?",
isImmediateExpression = true
)
getPresentationFunction.body.add("PorkElementHelpers.presentationOf(this)")
kotlinClass.functions.add(getPresentationFunction)
write("${type.name}Element.kt", KotlinWriter(kotlinClass)) write("${type.name}Element.kt", KotlinWriter(kotlinClass))
} }

View File

@ -195,7 +195,7 @@ class KotlinWriter() {
appendLine("package $pkg") appendLine("package $pkg")
appendLine() appendLine()
for (import in imports) { for (import in imports.toSortedSet()) {
appendLine("import $import") appendLine("import $import")
} }

View File

@ -0,0 +1,23 @@
package gay.pizza.pork.idea
import com.intellij.openapi.util.TextRange
import com.intellij.psi.AbstractElementManipulator
import com.intellij.psi.PsiFileFactory
import com.intellij.psi.impl.PsiFileFactoryImpl
import com.intellij.psi.util.elementType
import gay.pizza.pork.idea.psi.gen.PorkElement
class PorkElementManipulator : AbstractElementManipulator<PorkElement>() {
override fun handleContentChange(element: PorkElement, range: TextRange, newContent: String): PorkElement? {
val sourceText = element.text
val beforeText = sourceText.substring(0, range.startOffset)
val afterText = sourceText.substring(range.endOffset)
val changedText = beforeText + newContent + afterText
return element.replace(produce(element, changedText)) as PorkElement?
}
fun produce(element: PorkElement, changed: String): PorkElement {
val factory = PsiFileFactory.getInstance(element.project) as PsiFileFactoryImpl
return factory.createElementFromText(changed, PorkLanguage, element.elementType!!, element.context) as PorkElement
}
}

View File

@ -1,11 +0,0 @@
package gay.pizza.pork.idea
import com.intellij.model.Pointer
import com.intellij.model.Symbol
@Suppress("UnstableApiUsage")
data class PorkFunctionSymbol(val id: String) : Symbol {
override fun createPointer(): Pointer<out Symbol> {
return Pointer { this }
}
}

View File

@ -1,6 +0,0 @@
package gay.pizza.pork.idea
import com.intellij.openapi.util.Key
import gay.pizza.pork.ast.Node
object PorkNodeKey : Key<Node>("PorkAstNode")

View File

@ -3,18 +3,26 @@ package gay.pizza.pork.idea
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.lang.PsiBuilder import com.intellij.lang.PsiBuilder
import com.intellij.lang.PsiParser import com.intellij.lang.PsiParser
import com.intellij.psi.impl.PsiElementBase
import com.intellij.psi.tree.IElementType import com.intellij.psi.tree.IElementType
import com.intellij.psi.tree.IFileElementType
import gay.pizza.pork.ast.NodeType
import gay.pizza.pork.ast.parse
import gay.pizza.pork.parser.Parser import gay.pizza.pork.parser.Parser
class PorkParser : PsiParser { class PorkParser : PsiParser {
override fun parse(root: IElementType, builder: PsiBuilder): ASTNode { override fun parse(root: IElementType, builder: PsiBuilder): ASTNode {
val nodeTypeForParse = if (root is IFileElementType) {
NodeType.CompilationUnit
} else {
PorkElementTypes.nodeTypeFor(root) ?:
throw RuntimeException("Unable to parse element type: $root")
}
val marker = builder.mark() val marker = builder.mark()
val psiBuilderMarkAttribution = PsiBuilderMarkAttribution(builder) val psiBuilderMarkAttribution = PsiBuilderMarkAttribution(builder)
val source = PsiBuilderTokenSource(builder) val source = PsiBuilderTokenSource(builder)
val parser = Parser(source, psiBuilderMarkAttribution) val parser = Parser(source, psiBuilderMarkAttribution)
try { try {
parser.parseCompilationUnit() parser.parse(nodeTypeForParse)
} catch (_: ExitParser) {} } catch (_: ExitParser) {}
marker.done(root) marker.done(root)
return builder.treeBuilt return builder.treeBuilt

View File

@ -1,27 +0,0 @@
package gay.pizza.pork.idea
import com.intellij.model.Symbol
import com.intellij.model.psi.PsiSymbolDeclaration
import com.intellij.openapi.util.TextRange
import com.intellij.psi.PsiElement
import com.intellij.psi.util.elementType
import gay.pizza.pork.ast.NodeType
@Suppress("UnstableApiUsage")
class PorkSymbolDeclaration(val element: PsiElement) : PsiSymbolDeclaration {
override fun getDeclaringElement(): PsiElement = element
override fun getRangeInDeclaringElement(): TextRange {
return getSymbolElement().textRange
}
override fun getSymbol(): Symbol {
val element = getSymbolElement()
return PorkFunctionSymbol(element.text.trim())
}
private fun getSymbolElement(): PsiElement {
return element.children.first {
it.elementType == PorkElementTypes.elementTypeFor(NodeType.Symbol)
}
}
}

View File

@ -1,21 +0,0 @@
package gay.pizza.pork.idea
import com.intellij.model.psi.PsiSymbolDeclaration
import com.intellij.model.psi.PsiSymbolDeclarationProvider
import com.intellij.psi.PsiElement
import com.intellij.psi.util.elementType
import gay.pizza.pork.ast.NodeType
@Suppress("UnstableApiUsage")
class PorkSymbolDeclarationProvider : PsiSymbolDeclarationProvider {
override fun getDeclarations(
element: PsiElement,
offsetInElement: Int
): MutableCollection<out PsiSymbolDeclaration> {
val symbolDeclarations = mutableListOf<PsiSymbolDeclaration>()
if (element.elementType == PorkElementTypes.elementTypeFor(NodeType.FunctionDefinition)) {
symbolDeclarations.add(PorkSymbolDeclaration(element))
}
return symbolDeclarations
}
}

View File

@ -5,11 +5,8 @@ import gay.pizza.pork.ast.Node
import gay.pizza.pork.ast.NodeType import gay.pizza.pork.ast.NodeType
import gay.pizza.pork.parser.ParseError import gay.pizza.pork.parser.ParseError
import gay.pizza.pork.parser.ParserNodeAttribution import gay.pizza.pork.parser.ParserNodeAttribution
import java.util.IdentityHashMap
class PsiBuilderMarkAttribution(val builder: PsiBuilder) : ParserNodeAttribution() { class PsiBuilderMarkAttribution(val builder: PsiBuilder) : ParserNodeAttribution() {
private val map = IdentityHashMap<Node, Node>()
override fun <T : Node> guarded(type: NodeType?, block: () -> T): T { override fun <T : Node> guarded(type: NodeType?, block: () -> T): T {
val marker = builder.mark() val marker = builder.mark()
val result = try { val result = try {
@ -32,10 +29,6 @@ class PsiBuilderMarkAttribution(val builder: PsiBuilder) : ParserNodeAttribution
marker.done(PorkElementTypes.FailedToParse) marker.done(PorkElementTypes.FailedToParse)
throw e throw e
} }
if (map[result] != null) {
marker.drop()
}
map[result] = result
return result return result
} }
} }

View File

@ -1,31 +1,74 @@
package gay.pizza.pork.idea.psi package gay.pizza.pork.idea.psi
import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import com.intellij.psi.PsiElement import com.intellij.psi.PsiElement
import com.intellij.psi.PsiFileFactory
import com.intellij.psi.PsiReference import com.intellij.psi.PsiReference
import com.intellij.psi.impl.PsiFileFactoryImpl
import com.intellij.psi.util.PsiTreeUtil
import com.intellij.psi.util.childrenOfType import com.intellij.psi.util.childrenOfType
import com.intellij.util.PlatformIcons
import gay.pizza.pork.ast.NodeType import gay.pizza.pork.ast.NodeType
import gay.pizza.pork.idea.PorkElementTypes import gay.pizza.pork.idea.PorkElementTypes
import gay.pizza.pork.idea.psi.gen.PorkElement import gay.pizza.pork.idea.PorkLanguage
import gay.pizza.pork.idea.psi.gen.PorkNamedElement import gay.pizza.pork.idea.psi.gen.*
import gay.pizza.pork.idea.psi.gen.SymbolElement import javax.swing.Icon
object PorkElementHelpers { object PorkElementHelpers {
private val symbolElementType = PorkElementTypes.elementTypeFor(NodeType.Symbol) private val symbolElementType = PorkElementTypes.elementTypeFor(NodeType.Symbol)
fun nameOfNamedElement(element: PorkNamedElement): String? { fun nameOfNamedElement(element: PorkNamedElement): String? {
val child = element.node.findChildByType(symbolElementType) val child = symbolOf(element) ?: return null
return child?.text return child.text
} }
fun setNameOfNamedElement(element: PorkNamedElement, name: String): PsiElement = element fun setNameOfNamedElement(element: PorkNamedElement, name: String): PsiElement {
val child = symbolOf(element) ?: return element
val factory = PsiFileFactory.getInstance(element.project) as PsiFileFactoryImpl
val created = factory.createElementFromText(name, PorkLanguage, child.elementType, element.context) as PorkElement
element.node.replaceChild(child, created.node)
return element
}
fun symbolOf(element: PorkElement): ASTNode? {
var child = element.node.findChildByType(symbolElementType)
if (child == null) {
child = PsiTreeUtil.collectElementsOfType(element, SymbolElement::class.java).firstOrNull()?.node
}
return child
}
fun nameIdentifierOfNamedElement(element: PorkNamedElement): PsiElement? { fun nameIdentifierOfNamedElement(element: PorkNamedElement): PsiElement? {
val child = element.node.findChildByType(symbolElementType) return symbolOf(element)?.psi
return child?.psi
} }
fun referenceOfElement(element: PorkElement, type: NodeType): PsiReference? { fun referenceOfElement(element: PorkElement, type: NodeType): PsiReference? {
val textRangeOfSymbolInElement = element.childrenOfType<SymbolElement>().firstOrNull()?.textRangeInParent ?: return null val textRangeOfSymbolInElement = element.childrenOfType<SymbolElement>().firstOrNull()?.textRangeInParent ?: return null
return PorkIdentifierReference(element, textRangeOfSymbolInElement) return PorkIdentifierReference(element, textRangeOfSymbolInElement)
} }
fun iconOf(element: PorkElement): Icon? {
return when (element) {
is LetDefinitionElement -> PlatformIcons.FIELD_ICON
is FunctionDefinitionElement -> PlatformIcons.FUNCTION_ICON
is LetAssignmentElement -> PlatformIcons.VARIABLE_READ_ACCESS
is VarAssignmentElement -> PlatformIcons.VARIABLE_RW_ACCESS
is ArgumentSpecElement -> PlatformIcons.VARIABLE_READ_ACCESS
else -> null
}
}
fun presentationOf(element: PorkElement): ItemPresentation? {
val icon = iconOf(element)
if (element is FunctionDefinitionElement || element is LetDefinitionElement) {
return PorkPresentable(element.name, icon, element.containingFile.virtualFile?.name)
}
if (element is LetAssignmentElement || element is VarAssignmentElement) {
return PorkPresentable(element.name, icon)
}
return null
}
} }

View File

@ -17,7 +17,8 @@ class PorkIdentifierReference(element: PorkElement, textRange: TextRange) : Pork
} }
override fun getVariants(): Array<Any> { override fun getVariants(): Array<Any> {
return findAllCandidates().toTypedArray() val candidates = findAllCandidates()
return candidates.toTypedArray()
} }
fun findAllCandidates(name: String? = null): List<PorkElement> = fun findAllCandidates(name: String? = null): List<PorkElement> =
@ -25,9 +26,7 @@ class PorkIdentifierReference(element: PorkElement, textRange: TextRange) : Pork
fun findAnyLocals(name: String? = null): List<PorkElement> { fun findAnyLocals(name: String? = null): List<PorkElement> {
val functionDefinitionElement = PsiTreeUtil.getParentOfType(element, FunctionDefinitionElement::class.java) val functionDefinitionElement = PsiTreeUtil.getParentOfType(element, FunctionDefinitionElement::class.java)
if (functionDefinitionElement == null) { ?: return emptyList()
return emptyList()
}
val locals = mutableListOf<PorkElement>() val locals = mutableListOf<PorkElement>()
fun check(localCandidate: PsiElement, upward: Boolean) { fun check(localCandidate: PsiElement, upward: Boolean) {
@ -35,10 +34,6 @@ class PorkIdentifierReference(element: PorkElement, textRange: TextRange) : Pork
return return
} }
if (localCandidate == element) {
return
}
if (localCandidate is ArgumentSpecElement || if (localCandidate is ArgumentSpecElement ||
localCandidate is LetAssignmentElement || localCandidate is LetAssignmentElement ||
localCandidate is VarAssignmentElement) { localCandidate is VarAssignmentElement) {
@ -46,8 +41,10 @@ class PorkIdentifierReference(element: PorkElement, textRange: TextRange) : Pork
} }
if (localCandidate is ForInElement) { if (localCandidate is ForInElement) {
val forInItem = localCandidate.childrenOfType<ForInItemElement>().first() val forInItem = localCandidate.childrenOfType<ForInItemElement>().firstOrNull()
locals.add(forInItem) if (forInItem != null) {
locals.add(forInItem)
}
} }
localCandidate.children.forEach { check(it, false) } localCandidate.children.forEach { check(it, false) }
@ -55,6 +52,9 @@ class PorkIdentifierReference(element: PorkElement, textRange: TextRange) : Pork
PsiTreeUtil.treeWalkUp(element, functionDefinitionElement) { _, localCandidate -> PsiTreeUtil.treeWalkUp(element, functionDefinitionElement) { _, localCandidate ->
if (localCandidate != null) { if (localCandidate != null) {
if (element == functionDefinitionElement) {
return@treeWalkUp true
}
check(localCandidate, true) check(localCandidate, true)
} }
true true
@ -62,7 +62,8 @@ class PorkIdentifierReference(element: PorkElement, textRange: TextRange) : Pork
val argumentSpecElements = functionDefinitionElement.childrenOfType<ArgumentSpecElement>() val argumentSpecElements = functionDefinitionElement.childrenOfType<ArgumentSpecElement>()
locals.addAll(argumentSpecElements) locals.addAll(argumentSpecElements)
return locals.filter { it.name == name } val finalLocals = locals.distinctBy { it.textRange }
return finalLocals.filter { if (name != null) it.name == name else true }
} }
fun findAnyDefinitions(name: String? = null): List<PorkElement> { fun findAnyDefinitions(name: String? = null): List<PorkElement> {

View File

@ -0,0 +1,10 @@
package gay.pizza.pork.idea.psi
import com.intellij.navigation.ItemPresentation
import javax.swing.Icon
class PorkPresentable(val porkText: String?, val porkIcon: Icon? = null, val porkLocation: String? = null) : ItemPresentation {
override fun getPresentableText(): String? = porkText
override fun getIcon(unused: Boolean): Icon? = porkIcon
override fun getLocationString(): String? = porkLocation
}

View File

@ -1,9 +1,11 @@
// GENERATED CODE FROM PORK AST CODEGEN // GENERATED CODE FROM PORK AST CODEGEN
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.psi.PsiElement
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import com.intellij.psi.PsiElement
import gay.pizza.pork.idea.psi.PorkElementHelpers import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class ArgumentSpecElement(node: ASTNode) : PorkNamedElement(node) { class ArgumentSpecElement(node: ASTNode) : PorkNamedElement(node) {
override fun getName(): String? = override fun getName(): String? =
@ -14,4 +16,10 @@ class ArgumentSpecElement(node: ASTNode) : PorkNamedElement(node) {
override fun getNameIdentifier(): PsiElement? = override fun getNameIdentifier(): PsiElement? =
PorkElementHelpers.nameIdentifierOfNamedElement(this) PorkElementHelpers.nameIdentifierOfNamedElement(this)
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
} }

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class BlockElement(node: ASTNode) : PorkElement(node) class BlockElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class BooleanLiteralElement(node: ASTNode) : PorkElement(node) class BooleanLiteralElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class BreakElement(node: ASTNode) : PorkElement(node) class BreakElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class CompilationUnitElement(node: ASTNode) : PorkElement(node) class CompilationUnitElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class ContinueElement(node: ASTNode) : PorkElement(node) class ContinueElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class DoubleLiteralElement(node: ASTNode) : PorkElement(node) class DoubleLiteralElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class ForInElement(node: ASTNode) : PorkElement(node) class ForInElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -1,9 +1,11 @@
// GENERATED CODE FROM PORK AST CODEGEN // GENERATED CODE FROM PORK AST CODEGEN
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.psi.PsiElement
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import com.intellij.psi.PsiElement
import gay.pizza.pork.idea.psi.PorkElementHelpers import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class ForInItemElement(node: ASTNode) : PorkNamedElement(node) { class ForInItemElement(node: ASTNode) : PorkNamedElement(node) {
override fun getName(): String? = override fun getName(): String? =
@ -14,4 +16,10 @@ class ForInItemElement(node: ASTNode) : PorkNamedElement(node) {
override fun getNameIdentifier(): PsiElement? = override fun getNameIdentifier(): PsiElement? =
PorkElementHelpers.nameIdentifierOfNamedElement(this) PorkElementHelpers.nameIdentifierOfNamedElement(this)
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
} }

View File

@ -1,12 +1,20 @@
// GENERATED CODE FROM PORK AST CODEGEN // GENERATED CODE FROM PORK AST CODEGEN
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.psi.PsiReference
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import com.intellij.psi.PsiReference
import gay.pizza.pork.ast.NodeType import gay.pizza.pork.ast.NodeType
import gay.pizza.pork.idea.psi.PorkElementHelpers import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class FunctionCallElement(node: ASTNode) : PorkElement(node) { class FunctionCallElement(node: ASTNode) : PorkElement(node) {
override fun getReference(): PsiReference? = override fun getReference(): PsiReference? =
PorkElementHelpers.referenceOfElement(this, NodeType.FunctionDefinition) PorkElementHelpers.referenceOfElement(this, NodeType.FunctionDefinition)
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
} }

View File

@ -1,9 +1,11 @@
// GENERATED CODE FROM PORK AST CODEGEN // GENERATED CODE FROM PORK AST CODEGEN
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.psi.PsiElement
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import com.intellij.psi.PsiElement
import gay.pizza.pork.idea.psi.PorkElementHelpers import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class FunctionDefinitionElement(node: ASTNode) : PorkNamedElement(node) { class FunctionDefinitionElement(node: ASTNode) : PorkNamedElement(node) {
override fun getName(): String? = override fun getName(): String? =
@ -14,4 +16,10 @@ class FunctionDefinitionElement(node: ASTNode) : PorkNamedElement(node) {
override fun getNameIdentifier(): PsiElement? = override fun getNameIdentifier(): PsiElement? =
PorkElementHelpers.nameIdentifierOfNamedElement(this) PorkElementHelpers.nameIdentifierOfNamedElement(this)
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
} }

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class IfElement(node: ASTNode) : PorkElement(node) class IfElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class ImportDeclarationElement(node: ASTNode) : PorkElement(node) class ImportDeclarationElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class IndexedByElement(node: ASTNode) : PorkElement(node) class IndexedByElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class InfixOperationElement(node: ASTNode) : PorkElement(node) class InfixOperationElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class IntegerLiteralElement(node: ASTNode) : PorkElement(node) class IntegerLiteralElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -1,9 +1,11 @@
// GENERATED CODE FROM PORK AST CODEGEN // GENERATED CODE FROM PORK AST CODEGEN
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.psi.PsiElement
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import com.intellij.psi.PsiElement
import gay.pizza.pork.idea.psi.PorkElementHelpers import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class LetAssignmentElement(node: ASTNode) : PorkNamedElement(node) { class LetAssignmentElement(node: ASTNode) : PorkNamedElement(node) {
override fun getName(): String? = override fun getName(): String? =
@ -14,4 +16,10 @@ class LetAssignmentElement(node: ASTNode) : PorkNamedElement(node) {
override fun getNameIdentifier(): PsiElement? = override fun getNameIdentifier(): PsiElement? =
PorkElementHelpers.nameIdentifierOfNamedElement(this) PorkElementHelpers.nameIdentifierOfNamedElement(this)
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
} }

View File

@ -1,9 +1,11 @@
// GENERATED CODE FROM PORK AST CODEGEN // GENERATED CODE FROM PORK AST CODEGEN
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.psi.PsiElement
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import com.intellij.psi.PsiElement
import gay.pizza.pork.idea.psi.PorkElementHelpers import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class LetDefinitionElement(node: ASTNode) : PorkNamedElement(node) { class LetDefinitionElement(node: ASTNode) : PorkNamedElement(node) {
override fun getName(): String? = override fun getName(): String? =
@ -14,4 +16,10 @@ class LetDefinitionElement(node: ASTNode) : PorkNamedElement(node) {
override fun getNameIdentifier(): PsiElement? = override fun getNameIdentifier(): PsiElement? =
PorkElementHelpers.nameIdentifierOfNamedElement(this) PorkElementHelpers.nameIdentifierOfNamedElement(this)
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
} }

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class ListLiteralElement(node: ASTNode) : PorkElement(node) class ListLiteralElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class LongLiteralElement(node: ASTNode) : PorkElement(node) class LongLiteralElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class NativeElement(node: ASTNode) : PorkElement(node) class NativeElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class NoneLiteralElement(node: ASTNode) : PorkElement(node) class NoneLiteralElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class ParenthesesElement(node: ASTNode) : PorkElement(node) class ParenthesesElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class PrefixOperationElement(node: ASTNode) : PorkElement(node) class PrefixOperationElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class SetAssignmentElement(node: ASTNode) : PorkElement(node) class SetAssignmentElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class StringLiteralElement(node: ASTNode) : PorkElement(node) class StringLiteralElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class SuffixOperationElement(node: ASTNode) : PorkElement(node) class SuffixOperationElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class SymbolElement(node: ASTNode) : PorkElement(node) class SymbolElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -1,12 +1,30 @@
// GENERATED CODE FROM PORK AST CODEGEN // GENERATED CODE FROM PORK AST CODEGEN
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.psi.PsiReference
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import com.intellij.psi.PsiElement
import com.intellij.psi.PsiReference
import gay.pizza.pork.ast.NodeType import gay.pizza.pork.ast.NodeType
import gay.pizza.pork.idea.psi.PorkElementHelpers import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class SymbolReferenceElement(node: ASTNode) : PorkNamedElement(node) {
override fun getName(): String? =
PorkElementHelpers.nameOfNamedElement(this)
override fun setName(name: String): PsiElement =
PorkElementHelpers.setNameOfNamedElement(this, name)
override fun getNameIdentifier(): PsiElement? =
PorkElementHelpers.nameIdentifierOfNamedElement(this)
class SymbolReferenceElement(node: ASTNode) : PorkElement(node) {
override fun getReference(): PsiReference? = override fun getReference(): PsiReference? =
PorkElementHelpers.referenceOfElement(this, NodeType.Node) PorkElementHelpers.referenceOfElement(this, NodeType.Node)
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
} }

View File

@ -1,9 +1,11 @@
// GENERATED CODE FROM PORK AST CODEGEN // GENERATED CODE FROM PORK AST CODEGEN
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.psi.PsiElement
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import com.intellij.psi.PsiElement
import gay.pizza.pork.idea.psi.PorkElementHelpers import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class VarAssignmentElement(node: ASTNode) : PorkNamedElement(node) { class VarAssignmentElement(node: ASTNode) : PorkNamedElement(node) {
override fun getName(): String? = override fun getName(): String? =
@ -14,4 +16,10 @@ class VarAssignmentElement(node: ASTNode) : PorkNamedElement(node) {
override fun getNameIdentifier(): PsiElement? = override fun getNameIdentifier(): PsiElement? =
PorkElementHelpers.nameIdentifierOfNamedElement(this) PorkElementHelpers.nameIdentifierOfNamedElement(this)
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
} }

View File

@ -2,5 +2,14 @@
package gay.pizza.pork.idea.psi.gen package gay.pizza.pork.idea.psi.gen
import com.intellij.lang.ASTNode import com.intellij.lang.ASTNode
import com.intellij.navigation.ItemPresentation
import gay.pizza.pork.idea.psi.PorkElementHelpers
import javax.swing.Icon
class WhileElement(node: ASTNode) : PorkElement(node) class WhileElement(node: ASTNode) : PorkElement(node) {
override fun getIcon(flags: Int): Icon? =
PorkElementHelpers.iconOf(this)
override fun getPresentation(): ItemPresentation? =
PorkElementHelpers.presentationOf(this)
}

View File

@ -23,7 +23,9 @@
<lang.refactoringSupport <lang.refactoringSupport
language="Pork" language="Pork"
implementationClass="gay.pizza.pork.idea.PorkRefactoringSupportProvider"/> implementationClass="gay.pizza.pork.idea.PorkRefactoringSupportProvider"/>
<psi.declarationProvider implementation="gay.pizza.pork.idea.PorkSymbolDeclarationProvider"/> <lang.elementManipulator
implementationClass="gay.pizza.pork.idea.PorkElementManipulator"
forClass="gay.pizza.pork.idea.psi.gen.PorkElement"/>
</extensions> </extensions>
<applicationListeners> <applicationListeners>