@@ -13,17 +13,135 @@ export async function viewOthers(): Promise<void> {
13
13
return ;
14
14
}
15
15
16
- const open = ( item ) => {
17
- const uri = DocumentContentProvider . getUri ( item ) ;
18
- vscode . window . showTextDocument ( uri ) ;
16
+ const open = async ( item : string ) => {
17
+ const colonidx : number = item . indexOf ( ":" ) ;
18
+ if ( colonidx !== - 1 ) {
19
+ // A location is appened to the name of the other document
20
+ const options : vscode . TextDocumentShowOptions = { } ;
21
+
22
+ // Split the document name form the location
23
+ let loc = item . slice ( colonidx + 1 ) ;
24
+ item = item . slice ( 0 , colonidx ) ;
25
+ const uri = DocumentContentProvider . getUri ( item ) ;
26
+
27
+ if ( item . endsWith ( ".cls" ) ) {
28
+ // Locations in classes are of the format method+offset+namespace
29
+ loc = loc . slice ( 0 , loc . lastIndexOf ( "+" ) ) ;
30
+ let method = loc . slice ( 0 , loc . lastIndexOf ( "+" ) ) ;
31
+
32
+ // Properly delimit method name if it contains invalid characters
33
+ if ( method . match ( / ( ^ ( [ A - Z a - z ] | % ) $ ) | ( ^ ( [ A - Z a - z ] | % ) ( [ A - Z a - z ] | \d | [ ^ \x20 - \x7F ] ) + $ ) / g) === null ) {
34
+ method = '"' + method . replace ( / " / g, '""' ) + '"' ;
35
+ }
36
+
37
+ // Find the location of the given method in the class
38
+ const symbols : vscode . DocumentSymbol [ ] = await vscode . commands . executeCommand (
39
+ "vscode.executeDocumentSymbolProvider" ,
40
+ uri
41
+ ) ;
42
+ if ( symbols !== undefined ) {
43
+ for ( const symbol of symbols [ 0 ] . children ) {
44
+ if ( symbol . name === method ) {
45
+ // This is symbol that the location is in
46
+ const doc = await vscode . workspace . openTextDocument ( uri ) ;
47
+
48
+ // Need to find the actual start of the method
49
+ for (
50
+ let methodlinenum = symbol . selectionRange . start . line ;
51
+ methodlinenum <= symbol . range . end . line ;
52
+ methodlinenum ++
53
+ ) {
54
+ const methodlinetext : string = doc . lineAt ( methodlinenum ) . text . trim ( ) ;
55
+ if ( methodlinetext . endsWith ( "{" ) ) {
56
+ // This is the last line of the method definition, so count from here
57
+ const selectionline : number = methodlinenum + + loc . slice ( loc . lastIndexOf ( "+" ) + 1 ) ;
58
+ options . selection = new vscode . Range ( selectionline , 0 , selectionline , 0 ) ;
59
+ break ;
60
+ }
61
+ }
62
+ break ;
63
+ }
64
+ }
65
+ }
66
+ } else {
67
+ if ( item . endsWith ( ".mac" ) ) {
68
+ // Locations in MAC routines are of the format +offset+namespace
69
+ loc = loc . slice ( 0 , loc . lastIndexOf ( "+" ) ) ;
70
+ }
71
+ // Locations in INT routines are of the format +offset
72
+ const linenum : number = + loc . slice ( 1 ) ;
73
+ options . selection = new vscode . Range ( linenum , 0 , linenum , 0 ) ;
74
+ }
75
+ vscode . window . showTextDocument ( uri , options ) ;
76
+ } else {
77
+ const uri = DocumentContentProvider . getUri ( item ) ;
78
+ vscode . window . showTextDocument ( uri ) ;
79
+ }
19
80
} ;
20
81
21
82
const getOthers = ( info ) => {
22
83
return info . result . content [ 0 ] . others ;
23
84
} ;
85
+
24
86
const api = new AtelierAPI ( file . uri ) ;
87
+ let indexarg : string = file . name ;
88
+ const cursorpos : vscode . Position = vscode . window . activeTextEditor . selection . active ;
89
+ const fileExt : string = file . name . split ( "." ) . pop ( ) . toLowerCase ( ) ;
90
+
91
+ if ( api . config . apiVersion >= 4 && ( fileExt === "cls" || fileExt === "mac" || fileExt === "int" ) ) {
92
+ // Send the server the current position in the document appended to the name if it supports it
93
+ let symbols : vscode . DocumentSymbol [ ] = await vscode . commands . executeCommand (
94
+ "vscode.executeDocumentSymbolProvider" ,
95
+ file . uri
96
+ ) ;
97
+ if ( symbols !== undefined ) {
98
+ if ( fileExt === "cls" ) {
99
+ symbols = symbols [ 0 ] . children ;
100
+ }
101
+
102
+ let currentSymbol : vscode . DocumentSymbol ;
103
+ for ( const symbol of symbols ) {
104
+ if ( symbol . range . contains ( cursorpos ) ) {
105
+ currentSymbol = symbol ;
106
+ break ;
107
+ }
108
+ }
109
+
110
+ if (
111
+ currentSymbol !== undefined &&
112
+ currentSymbol . kind === vscode . SymbolKind . Method &&
113
+ currentSymbol . detail . toLowerCase ( ) !== "query" &&
114
+ currentSymbol . name . charAt ( 0 ) !== '"' &&
115
+ currentSymbol . name . charAt ( currentSymbol . name . length - 1 ) !== '"'
116
+ ) {
117
+ // The current position is in a symbol that we can convert into a label+offset that the server understands
118
+ let offset : number = cursorpos . line - currentSymbol . selectionRange . start . line ;
119
+
120
+ if ( fileExt === "cls" ) {
121
+ // Need to find the actual start of the method
122
+ const currentdoc : vscode . TextDocument = vscode . window . activeTextEditor . document ;
123
+ for (
124
+ let methodlinenum = currentSymbol . selectionRange . start . line ;
125
+ methodlinenum <= currentSymbol . range . end . line ;
126
+ methodlinenum ++
127
+ ) {
128
+ const methodlinetext : string = currentdoc . lineAt ( methodlinenum ) . text . trim ( ) ;
129
+ if ( methodlinetext . endsWith ( "{" ) ) {
130
+ // This is the last line of the method definition, so count from here
131
+ offset = cursorpos . line - methodlinenum ;
132
+ break ;
133
+ }
134
+ }
135
+ }
136
+
137
+ offset = offset < 0 ? 0 : offset ;
138
+ indexarg = indexarg + ":" + currentSymbol . name + "+" + offset ;
139
+ }
140
+ }
141
+ }
142
+
25
143
return api
26
- . actionIndex ( [ file . name ] )
144
+ . actionIndex ( [ indexarg ] )
27
145
. then ( ( info ) => {
28
146
const listOthers = getOthers ( info ) || [ ] ;
29
147
if ( ! listOthers . length ) {
0 commit comments