Skip to content

Commit fa186b1

Browse files
committed
Add support for domain, leading, trailing, interior
1 parent f083bea commit fa186b1

File tree

3 files changed

+53
-9
lines changed

3 files changed

+53
-9
lines changed

packages/cursorless-engine/src/languages/ruby.ts

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -175,7 +175,6 @@ const nodeMatchers: Partial<
175175
"argument_list",
176176
),
177177
collectionKey: trailingMatcher(["pair[key]"], [":"]),
178-
className: "class[name]",
179178
name: [
180179
"assignment[left]",
181180
"operator_assignment[left]",

packages/cursorless-engine/src/processTargets/modifiers/scopeHandlers/TreeSitterScopeHandler.ts

Lines changed: 52 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -117,29 +117,73 @@ export class TreeSitterScopeHandler extends BaseScopeHandler {
117117
}
118118

119119
private matchToScope(editor: TextEditor, match: QueryMatch): TargetScope {
120+
const scopeTypeType = this.scopeType.type;
121+
120122
const contentRange = getNodeRange(
121-
match.captures.find((capture) => capture.name === this.scopeType.type)!
122-
.node,
123+
match.captures.find((capture) => capture.name === scopeTypeType)!.node,
124+
);
125+
126+
const domain =
127+
getRelatedRange(match, scopeTypeType, "domain") ?? contentRange;
128+
129+
const removalRange = getRelatedRange(match, scopeTypeType, "removal");
130+
131+
const leadingDelimiterRange = getRelatedRange(
132+
match,
133+
scopeTypeType,
134+
"leading",
135+
);
136+
137+
const trailingDelimiterRange = getRelatedRange(
138+
match,
139+
scopeTypeType,
140+
"trailing",
123141
);
124142

143+
const interiorRange = getRelatedRange(match, scopeTypeType, "interior");
144+
125145
return {
126146
editor,
127-
// FIXME: Actually get domain
128-
domain: contentRange,
147+
domain,
129148
getTarget: (isReversed) =>
130149
new ScopeTypeTarget({
131-
scopeTypeType: this.scopeType.type,
150+
scopeTypeType,
132151
editor,
133152
isReversed,
134153
contentRange,
135-
// FIXME: Actually get removalRange
136-
removalRange: contentRange,
137-
// FIXME: Other fields here
154+
removalRange,
155+
leadingDelimiterRange,
156+
trailingDelimiterRange,
157+
interiorRange,
158+
// FIXME: Add delimiter text
138159
}),
139160
};
140161
}
141162
}
142163

164+
/**
165+
* Gets the range of a node that is related to the scope. For example, if the
166+
* scope is "class name", the `domain` node would be the containing class.
167+
*
168+
* @param match The match to get the range from
169+
* @param scopeTypeType The type of the scope
170+
* @param relationship The relationship to get the range for, eg "domain", or "removal"
171+
* @returns A range or undefined if no range was found
172+
*/
173+
function getRelatedRange(
174+
match: QueryMatch,
175+
scopeTypeType: string,
176+
relationship: string,
177+
) {
178+
const relatedNode = match.captures.find(
179+
(capture) =>
180+
capture.name === `${scopeTypeType}.${relationship}` ||
181+
capture.name === relationship,
182+
)?.node;
183+
184+
return relatedNode == null ? undefined : getNodeRange(relatedNode);
185+
}
186+
143187
function positionToPoint(start: Position): Point | undefined {
144188
return { row: start.line, column: start.character };
145189
}

queries/ruby.scm

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,3 +13,4 @@
1313
(regex) @regularExpression
1414

1515
(class) @class
16+
(class name: (_) @className) @domain

0 commit comments

Comments
 (0)