fix: opened files are not highlighted with tree sitter

This happens because the tree-sitter nodes and trees are inaccessible when the files are opened
This commit is contained in:
Akash Yadav
2023-10-15 18:38:43 +05:30
parent d5910c6fc0
commit f2cfd865e8
5 changed files with 74 additions and 71 deletions
+6 -6
View File
@@ -1,17 +1,17 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="deploymentTargetDropDown">
<targetSelectedWithDropDown>
<runningDeviceTargetSelectedWithDropDown>
<Target>
<type value="QUICK_BOOT_TARGET" />
<type value="RUNNING_DEVICE_TARGET" />
<deviceKey>
<Key>
<type value="VIRTUAL_DEVICE_PATH" />
<value value="$USER_HOME$/.android/avd/Resizable_Experimental_API_33.avd" />
<type value="SERIAL_NUMBER" />
<value value="b36e6c44" />
</Key>
</deviceKey>
</Target>
</targetSelectedWithDropDown>
<timeTargetWasSelectedWithDropDown value="2023-10-14T04:10:20.140892617Z" />
</runningDeviceTargetSelectedWithDropDown>
<timeTargetWasSelectedWithDropDown value="2023-10-15T12:47:54.859420162Z" />
</component>
</project>
@@ -37,6 +37,7 @@ import com.itsaky.androidide.treesitter.api.TreeSitterQueryCapture
import com.itsaky.androidide.treesitter.api.TreeSitterQueryMatch
import com.itsaky.androidide.treesitter.string.UTF16String
import com.itsaky.androidide.treesitter.string.UTF16StringFactory
import com.itsaky.androidide.utils.ILogger
import io.github.rosemoe.sora.data.ObjectAllocator
import io.github.rosemoe.sora.editor.ts.spans.DefaultSpanFactory
import io.github.rosemoe.sora.editor.ts.spans.TsSpanFactory
@@ -158,6 +159,8 @@ open class TsAnalyzeManager(val languageSpec: TsLanguageSpec, var theme: TsTheme
@Synchronized
fun nextThreadId() = ++threadId
private val log = ILogger.newInstance("TsAnalyzeManager")
}
inner class TsLooperThread : Thread() {
@@ -219,14 +222,15 @@ open class TsAnalyzeManager(val languageSpec: TsLanguageSpec, var theme: TsTheme
}
fun updateCodeBlocks() {
if (languageSpec.blocksQuery.patternCount == 0 || !languageSpec.blocksQuery.canAccess()) {
if (languageSpec.blocksQuery.patternCount == 0
|| !languageSpec.blocksQuery.canAccess()
|| tree?.canAccess() != true
) {
return
}
val blocks = mutableListOf<CodeBlock>()
TSQueryCursor.create().use {
if (tree?.canAccess() != true) {
throw IllegalStateException("Cannot access tree")
}
val rootNode = tree!!.rootNode
it.exec(languageSpec.blocksQuery, rootNode)
@@ -274,8 +278,9 @@ open class TsAnalyzeManager(val languageSpec: TsLanguageSpec, var theme: TsTheme
val hasChanges = rootNode.hasChanges()
(rootNode as? TreeSitterNode?)?.recycle()
blocks.clear()
throw IllegalStateException(
"Tree closed while querying, rootNode.hasChanges=$hasChanges")
log.info(
"TsLooperThread.updateCodeBlock: Tree closed or edited while querying for code blocks. rootNode.hasChanges=$hasChanges")
break
}
match = it.nextMatch()
@@ -30,17 +30,17 @@ import com.itsaky.androidide.treesitter.TSTree
import com.itsaky.androidide.treesitter.api.TreeSitterNode
import com.itsaky.androidide.treesitter.api.TreeSitterQueryCapture
import com.itsaky.androidide.treesitter.api.TreeSitterQueryMatch
import com.itsaky.androidide.utils.ILogger
import io.github.rosemoe.sora.lang.brackets.BracketsProvider
import io.github.rosemoe.sora.lang.brackets.PairedBracket
import io.github.rosemoe.sora.text.Content
import java.lang.Math.max
import kotlin.math.max
class TsBracketPairs(
private val tree: TSTree,
private val languageSpec: TsLanguageSpec
) : BracketsProvider {
class TsBracketPairs(private val tree: TSTree, private val languageSpec: TsLanguageSpec) :
BracketsProvider {
companion object {
private val log = ILogger.newInstance("TsBracketPairs")
val OPEN_NAME = "editor.brackets.open"
val CLOSE_NAME = "editor.brackets.close"
@@ -48,62 +48,56 @@ class TsBracketPairs(
}
override fun getPairedBracketAt(text: Content, index: Int): PairedBracket? {
if (languageSpec.bracketsQuery.patternCount > 0 && languageSpec.bracketsQuery.canAccess() && tree.canAccess()) {
TSQueryCursor.create().use { cursor ->
cursor.setByteRange(max(0, index - 1) * 2, index * 2 + 1)
if (!tree.canAccess()) {
throw IllegalStateException("Cannot access tree")
}
val rootNode = tree.rootNode
cursor.exec(languageSpec.bracketsQuery, rootNode)
(rootNode as? TreeSitterNode?)?.recycle()
var match = cursor.nextMatch()
var matched = false
while (match != null && !matched) {
if (languageSpec.bracketsPredicator.doPredicate(
languageSpec.predicates,
text,
match
)
) {
var startNode: TSNode? = null
var endNode: TSNode? = null
for (capture in match.captures) {
val captureName =
languageSpec.bracketsQuery.getCaptureNameForId(capture.index)
if (captureName == OPEN_NAME || captureName == CLOSE_NAME) {
val node = capture.node
if (index >= node.startByte / 2 && index <= node.endByte / 2) {
matched = true
}
if (captureName == OPEN_NAME) {
startNode = node
} else {
endNode = node
}
if (languageSpec.bracketsQuery.patternCount <= 0
|| !languageSpec.bracketsQuery.canAccess()
|| !tree.canAccess()
) {
return null
}
TSQueryCursor.create().use { cursor ->
cursor.setByteRange(max(0, index - 1) * 2, index * 2 + 1)
val rootNode = tree.rootNode
cursor.exec(languageSpec.bracketsQuery, rootNode)
(rootNode as? TreeSitterNode?)?.recycle()
var match = cursor.nextMatch()
var matched = false
while (match != null && !matched) {
if (languageSpec.bracketsPredicator.doPredicate(languageSpec.predicates, text, match)) {
var startNode: TSNode? = null
var endNode: TSNode? = null
for (capture in match.captures) {
val captureName = languageSpec.bracketsQuery.getCaptureNameForId(capture.index)
if (captureName == OPEN_NAME || captureName == CLOSE_NAME) {
val node = capture.node
if (index >= node.startByte / 2 && index <= node.endByte / 2) {
matched = true
}
if (captureName == OPEN_NAME) {
startNode = node
} else {
endNode = node
}
(capture as? TreeSitterQueryCapture?)?.recycle()
}
if (matched && startNode != null && endNode != null) {
return PairedBracket(
startNode.startByte / 2,
(startNode.endByte - startNode.startByte) / 2,
endNode.startByte / 2,
(endNode.endByte - endNode.startByte) / 2
)
}
}
(match as? TreeSitterQueryMatch?)?.recycle()
if (!tree.canAccess() || rootNode.hasChanges()) {
val hasChanges = rootNode.hasChanges()
(rootNode as? TreeSitterNode?)?.recycle()
throw IllegalStateException(
"Tree closed or edited while querying, rootNode.hasChanges=$hasChanges")
(capture as? TreeSitterQueryCapture?)?.recycle()
}
if (matched && startNode != null && endNode != null) {
return PairedBracket(startNode.startByte / 2,
(startNode.endByte - startNode.startByte) / 2, endNode.startByte / 2,
(endNode.endByte - endNode.startByte) / 2)
}
match = cursor.nextMatch()
}
(match as? TreeSitterQueryMatch?)?.recycle()
if (!tree.canAccess() || rootNode.hasChanges()) {
val hasChanges = rootNode.hasChanges()
(rootNode as? TreeSitterNode?)?.recycle()
log.info("Tree closed or edited while querying, rootNode.hasChanges=$hasChanges")
return null
}
match = cursor.nextMatch()
}
}
return null
@@ -32,6 +32,7 @@ import com.itsaky.androidide.treesitter.api.TreeSitterNode
import com.itsaky.androidide.treesitter.api.TreeSitterQueryCapture
import com.itsaky.androidide.treesitter.api.TreeSitterQueryMatch
import com.itsaky.androidide.treesitter.string.UTF16String
import com.itsaky.androidide.utils.ILogger
import java.util.Stack
/**
@@ -47,6 +48,10 @@ class TsScopedVariables(tree: TSTree, text: UTF16String, val spec: TsLanguageSpe
private val rootScope: Scope
companion object {
private val log = ILogger.newInstance("TsScopedVariables")
}
init {
if (!tree.canAccess()) {
throw IllegalStateException("Cannot access tree")
@@ -69,8 +74,8 @@ class TsScopedVariables(tree: TSTree, text: UTF16String, val spec: TsLanguageSpe
val hasChanges = rootNode.hasChanges()
(rootNode as? TreeSitterNode?)?.recycle()
captures.clear()
throw IllegalStateException(
"Tree closed while querying, rootNode.hasChanges=$hasChanges")
log.info("Tree editor or closed while querying, rootNode.hasChanges=$hasChanges")
break
}
match = cursor.nextMatch()
@@ -74,7 +74,6 @@ abstract class TreeSitterLanguage(context: Context, lang: TSLanguage, type: Stri
langScheme.styles.forEach { tsTheme.putStyleRule(it.key, it.value.makeStyle()) }
analyzer.langScheme = languageScheme
analyzer.rerun()
}
}