Skip to content

Commit 521dd43

Browse files
Add range check to highlightsFromCursor (#187)
<!--- IMPORTANT: If this PR addresses multiple unrelated issues, it will be closed until separated. --> ### Description Fixes a bug found found by @cengelbart39 [on discord](https://canary.discord.com/channels/951544472238444645/952640521812193411/1104143145765187644) where a parser would consume ranges already consumed by injected languages. This caused the injected ranges to be realized as plain text, when they should have been kept as their injected language's highlights. This should have been avoided by the call to `query.setRange(range)` on line [43 in TreeSitterClient+Highlight.swift](https://github.com/CodeEditApp/CodeEditTextView/blob/045bd359ef9c4addf2a5bf51e22ba660d69c5d10/Sources/CodeEditTextView/TreeSitter/TreeSitterClient%2BHighlight.swift#L44) but it was found that for some reason in the case found by @cengelbart39 it just didn't work. To fix, an additional check was added in `highlightsFromCursor` to only take any ranges that have indices in the intersection of it's range and the included range. ### Related Issues <!--- REQUIRED: Tag all related issues (e.g. * #123) --> <!--- If this PR resolves the issue please specify (e.g. * closes #123) --> <!--- If this PR addresses multiple issues, these issues must be related to one other --> * See discord link. ### Checklist <!--- Add things that are not yet implemented above --> - [x] I read and understood the [contributing guide](https://github.com/CodeEditApp/CodeEdit/blob/main/CONTRIBUTING.md) as well as the [code of conduct](https://github.com/CodeEditApp/CodeEdit/blob/main/CODE_OF_CONDUCT.md) - [x] The issues this PR addresses are related to each other - [x] My changes generate no new warnings - [x] My code builds and runs on my machine - [x] My changes are all related to the related issue above - [x] I documented my code ### Screenshots Before: https://user-images.githubusercontent.com/35942988/236696171-d30dfd7b-8545-4396-8aa8-490ceac65551.mov After: https://user-images.githubusercontent.com/35942988/236697575-3f605c0d-3dda-45c2-8f69-0f41148f1c2d.mov
1 parent b60e0fc commit 521dd43

File tree

1 file changed

+10
-5
lines changed

1 file changed

+10
-5
lines changed

Sources/CodeEditTextView/TreeSitter/TreeSitterClient+Highlight.swift

+10-5
Original file line numberDiff line numberDiff line change
@@ -44,23 +44,28 @@ extension TreeSitterClient {
4444
cursor.setRange(range)
4545
cursor.matchLimit = Constants.treeSitterMatchLimit
4646

47-
return highlightsFromCursor(cursor: ResolvingQueryCursor(cursor: cursor))
47+
return highlightsFromCursor(cursor: ResolvingQueryCursor(cursor: cursor), includedRange: range)
4848
}
4949

5050
/// Resolves a query cursor to the highlight ranges it contains.
5151
/// **Must be called on the main thread**
52-
/// - Parameter cursor: The cursor to resolve.
52+
/// - Parameters:
53+
/// - cursor: The cursor to resolve.
54+
/// - includedRange: The range to include highlights from.
5355
/// - Returns: Any highlight ranges contained in the cursor.
54-
internal func highlightsFromCursor(cursor: ResolvingQueryCursor) -> [HighlightRange] {
56+
internal func highlightsFromCursor(cursor: ResolvingQueryCursor, includedRange: NSRange) -> [HighlightRange] {
5557
cursor.prepare(with: self.textProvider)
5658
return cursor
5759
.flatMap { $0.captures }
5860
.compactMap {
61+
// Sometimes `cursor.setRange` just doesnt work :( so we have to do a redundant check for a valid range
62+
// in the included range
63+
let intersectionRange = $0.range.intersection(includedRange) ?? .zero
5964
// Some languages add an "@spell" capture to indicate a portion of text that should be spellchecked
6065
// (usually comments). But this causes other captures in the same range to be overriden. So we ignore
6166
// that specific capture type.
62-
if $0.name != "spell" && $0.name != "injection.content" {
63-
return HighlightRange(range: $0.range, capture: CaptureName.fromString($0.name ?? ""))
67+
if intersectionRange.length > 0 && $0.name != "spell" && $0.name != "injection.content" {
68+
return HighlightRange(range: intersectionRange, capture: CaptureName.fromString($0.name ?? ""))
6469
}
6570
return nil
6671
}

0 commit comments

Comments
 (0)