@@ -24,6 +24,8 @@ import {
24
24
SelectionWithEditor ,
25
25
Target ,
26
26
TypedSelection ,
27
+ Position as TargetPosition ,
28
+ InsideOutsideType ,
27
29
} from "./Types" ;
28
30
29
31
export default function processTargets (
@@ -199,19 +201,15 @@ function getSelectionsFromMark(
199
201
return context . sourceMark ;
200
202
201
203
case "cursorToken" : {
202
- const tokens = context . currentSelections . map ( ( selection ) => {
203
- const token = context . navigationMap . getTokenForRange (
204
- selection . selection
205
- ) ;
206
- if ( token == null ) {
207
- throw new Error ( "Couldn't find mark under cursor" ) ;
204
+ const tokenSelections = context . currentSelections . map ( ( selection ) => {
205
+ const tokenSelection =
206
+ context . navigationMap . getTokenSelectionForSelection ( selection ) ;
207
+ if ( tokenSelection == null ) {
208
+ throw new Error ( "Couldn't find token in selection" ) ;
208
209
}
209
- return token ;
210
+ return tokenSelection ;
210
211
} ) ;
211
- return tokens . map ( ( token ) => ( {
212
- selection : new Selection ( token . range . start , token . range . end ) ,
213
- editor : token . editor ,
214
- } ) ) ;
212
+ return tokenSelections ;
215
213
}
216
214
217
215
case "decoratedSymbol" :
@@ -334,6 +332,15 @@ function transformSelection(
334
332
const activeIndex =
335
333
modifier . active < 0 ? modifier . active + pieces . length : modifier . active ;
336
334
335
+ if (
336
+ anchorIndex < 0 ||
337
+ activeIndex < 0 ||
338
+ anchorIndex >= pieces . length ||
339
+ activeIndex >= pieces . length
340
+ ) {
341
+ throw new Error ( "Subtoken index out of range" ) ;
342
+ }
343
+
337
344
const isReversed = activeIndex < anchorIndex ;
338
345
339
346
const anchor = selection . selection . start . translate (
@@ -461,6 +468,8 @@ function createTypedSelection(
461
468
selectionContext : getTokenSelectionContext (
462
469
selection ,
463
470
modifier ,
471
+ position ,
472
+ insideOutsideType ,
464
473
selectionContext
465
474
) ,
466
475
} ;
@@ -600,6 +609,8 @@ function performPositionAdjustment(
600
609
function getTokenSelectionContext (
601
610
selection : SelectionWithEditor ,
602
611
modifier : Modifier ,
612
+ position : TargetPosition ,
613
+ insideOutsideType : InsideOutsideType ,
603
614
selectionContext : SelectionContext
604
615
) : SelectionContext {
605
616
if ( ! isSelectionContextEmpty ( selectionContext ) ) {
@@ -611,32 +622,38 @@ function getTokenSelectionContext(
611
622
612
623
const document = selection . editor . document ;
613
624
const { start, end } = selection . selection ;
614
-
615
- const startLine = document . lineAt ( start ) ;
616
- const leadingText = startLine . text . slice ( 0 , start . character ) ;
617
- const leadingDelimiters = leadingText . match ( / \s + $ / ) ;
618
- const leadingDelimiterRange =
619
- leadingDelimiters != null
620
- ? new Range (
621
- start . line ,
622
- start . character - leadingDelimiters [ 0 ] . length ,
623
- start . line ,
624
- start . character
625
- )
626
- : null ;
627
-
628
625
const endLine = document . lineAt ( end ) ;
629
- const trailingText = endLine . text . slice ( end . character ) ;
630
- const trailingDelimiters = trailingText . match ( / ^ \s + / ) ;
631
- const trailingDelimiterRange =
632
- trailingDelimiters != null
633
- ? new Range (
634
- end . line ,
635
- end . character ,
636
- end . line ,
637
- end . character + trailingDelimiters [ 0 ] . length
638
- )
639
- : null ;
626
+ let leadingDelimiterRange , trailingDelimiterRange ;
627
+
628
+ // Position start/end of has no delimiter
629
+ if ( position !== "before" || insideOutsideType !== "inside" ) {
630
+ const startLine = document . lineAt ( start ) ;
631
+ const leadingText = startLine . text . slice ( 0 , start . character ) ;
632
+ const leadingDelimiters = leadingText . match ( / \s + $ / ) ;
633
+ leadingDelimiterRange =
634
+ leadingDelimiters != null
635
+ ? new Range (
636
+ start . line ,
637
+ start . character - leadingDelimiters [ 0 ] . length ,
638
+ start . line ,
639
+ start . character
640
+ )
641
+ : null ;
642
+ }
643
+
644
+ if ( position !== "after" || insideOutsideType !== "inside" ) {
645
+ const trailingText = endLine . text . slice ( end . character ) ;
646
+ const trailingDelimiters = trailingText . match ( / ^ \s + / ) ;
647
+ trailingDelimiterRange =
648
+ trailingDelimiters != null
649
+ ? new Range (
650
+ end . line ,
651
+ end . character ,
652
+ end . line ,
653
+ end . character + trailingDelimiters [ 0 ] . length
654
+ )
655
+ : null ;
656
+ }
640
657
641
658
const isInDelimitedList =
642
659
( leadingDelimiterRange != null || trailingDelimiterRange != null ) &&
0 commit comments