@@ -3,38 +3,31 @@ local files = require 'files'
33local guide = require ' parser.guide'
44local define = require ' proto.define'
55local util = require ' utility'
6- local vm = require ' vm '
6+ local subber = require ' core.substring '
77
8- local function buildName (source , text )
9- local uri = guide .getUri (source )
10- local state = files .getState (uri )
11- local startOffset = guide .positionToOffset (state , source .start )
8+ local function buildName (source , sub )
129 if source .type == ' setmethod'
1310 or source .type == ' getmethod' then
1411 if source .method then
15- local finishOffset = guide .positionToOffset (state , source .method .finish )
16- return text :sub (startOffset + 1 , finishOffset )
12+ return sub (source .start + 1 , source .method .finish )
1713 end
1814 end
1915 if source .type == ' setfield'
2016 or source .type == ' tablefield'
2117 or source .type == ' getfield' then
2218 if source .field then
23- local finishOffset = guide .positionToOffset (state , source .field .finish )
24- return text :sub (startOffset + 1 , finishOffset )
19+ return sub (source .start + 1 , source .field .finish )
2520 end
2621 end
2722 if source .type == ' tableindex' then
2823 if source .index then
29- local finishOffset = guide .positionToOffset (state , source .finish )
30- return text :sub (startOffset + 1 , finishOffset )
24+ return sub (source .start + 1 , source .finish )
3125 end
3226 end
3327 if source .type == ' tableexp' then
3428 return (' [%d]' ):format (source .tindex )
3529 end
36- local finishOffset = guide .positionToOffset (state , source .finish )
37- return text :sub (startOffset + 1 , finishOffset )
30+ return sub (source .start + 1 , source .finish )
3831end
3932
4033local function buildFunctionParams (func )
@@ -56,8 +49,7 @@ local function buildFunctionParams(func)
5649 return table.concat (params , ' , ' )
5750end
5851
59- local function buildTable (tbl )
60- local uri = guide .getUri (tbl )
52+ local function buildTable (tbl , sub )
6153 local buf = {}
6254 for i = 1 , 5 do
6355 local field = tbl [i ]
@@ -69,9 +61,7 @@ local function buildTable(tbl)
6961 buf [# buf + 1 ] = (' %s' ):format (field .field [1 ])
7062 elseif field .type == ' tableindex'
7163 and field .index then
72- local view = vm .getInfer (field .index ):viewLiterals ()
73- or vm .getInfer (field .index ):view (uri )
74- buf [# buf + 1 ] = (' [%s]' ):format (view )
64+ buf [# buf + 1 ] = (' [%s]' ):format (sub (field .index .start + 1 , field .index .finish ))
7565 elseif field .type == ' tableexp' then
7666 buf [# buf + 1 ] = (' [%s]' ):format (field .tindex )
7767 end
@@ -82,25 +72,23 @@ local function buildTable(tbl)
8272 return table.concat (buf , ' , ' )
8373end
8474
85- local function buildArray (tbl )
86- local uri = guide .getUri (tbl )
75+ local function buildArray (tbl , sub )
8776 local buf = {}
8877 for i = 1 , 5 do
8978 local field = tbl [i ]
9079 if not field then
9180 break
9281 end
93- buf [# buf + 1 ] = vm .getInfer (field ):viewLiterals ()
94- or vm .getInfer (field ):view (uri )
82+ buf [# buf + 1 ] = sub (field .start + 1 , field .finish )
9583 end
9684 if # tbl > 5 then
9785 buf [# buf + 1 ] = (' ...(+%d)' ):format (# tbl - 5 )
9886 end
9987 return table.concat (buf , ' , ' )
10088end
10189
102- local function buildValue (source , text , used , symbols )
103- local name = buildName (source , text )
90+ local function buildValue (source , sub , used , symbols )
91+ local name = buildName (source , sub )
10492 local range , sRange , valueRange , kind
10593 local details = {}
10694 if source .type == ' local' then
@@ -175,12 +163,12 @@ local function buildValue(source, text, used, symbols)
175163 -- Array
176164 kind = define .SymbolKind .Array
177165 details [# details + 1 ] = ' ['
178- details [# details + 1 ] = buildArray (source .value )
166+ details [# details + 1 ] = buildArray (source .value , sub )
179167 details [# details + 1 ] = ' ]'
180168 else
181169 -- Object
182170 details [# details + 1 ] = ' {'
183- details [# details + 1 ] = buildTable (source .value )
171+ details [# details + 1 ] = buildTable (source .value , sub )
184172 details [# details + 1 ] = ' }'
185173 end
186174 end
@@ -211,7 +199,7 @@ local function buildValue(source, text, used, symbols)
211199 }
212200end
213201
214- local function buildAnonymousFunction (source , text , used , symbols )
202+ local function buildAnonymousFunction (source , sub , used , symbols )
215203 if used [source ] then
216204 return
217205 end
@@ -223,7 +211,7 @@ local function buildAnonymousFunction(source, text, used, symbols)
223211 elseif parent .type == ' callargs' then
224212 local call = parent .parent
225213 local node = call .node
226- head = buildName (node , text ) .. ' -> '
214+ head = buildName (node , sub ) .. ' -> '
227215 end
228216 symbols [# symbols + 1 ] = {
229217 name = ' ' ,
@@ -235,7 +223,54 @@ local function buildAnonymousFunction(source, text, used, symbols)
235223 }
236224end
237225
238- local function buildSource (source , text , used , symbols )
226+ local function buildBlock (source , sub , used , symbols )
227+ if used [source ] then
228+ return
229+ end
230+ used [source ] = true
231+ if source .type == ' if' then
232+ for _ , block in ipairs (source ) do
233+ symbols [# symbols + 1 ] = {
234+ name = block .type :gsub (' block$' , ' ' ),
235+ detail = sub (block .start + 1 , block .keyword [4 ] or block .keyword [2 ]),
236+ kind = define .SymbolKind .Package ,
237+ range = { block .start , block .finish },
238+ valueRange = { block .start , block .finish },
239+ selectionRange = { block .keyword [1 ], block .keyword [2 ] },
240+ }
241+ end
242+ elseif source .type == ' while' then
243+ symbols [# symbols + 1 ] = {
244+ name = ' while' ,
245+ detail = sub (source .start + 1 , source .keyword [4 ] or source .keyword [2 ]),
246+ kind = define .SymbolKind .Package ,
247+ range = { source .start , source .finish },
248+ valueRange = { source .start , source .finish },
249+ selectionRange = { source .keyword [1 ], source .keyword [2 ] },
250+ }
251+ elseif source .type == ' repeat' then
252+ symbols [# symbols + 1 ] = {
253+ name = ' repeat' ,
254+ detail = source .filter and sub (source .keyword [3 ] + 1 , source .filter .finish ) or ' ' ,
255+ kind = define .SymbolKind .Package ,
256+ range = { source .start , source .finish },
257+ valueRange = { source .start , source .finish },
258+ selectionRange = { source .keyword [1 ], source .keyword [2 ] },
259+ }
260+ elseif source .type == ' loop'
261+ or source .type == ' in' then
262+ symbols [# symbols + 1 ] = {
263+ name = ' for' ,
264+ detail = sub (source .start , source .keyword [4 ] or source .keyword [2 ]),
265+ kind = define .SymbolKind .Package ,
266+ range = { source .start , source .finish },
267+ valueRange = { source .start , source .finish },
268+ selectionRange = { source .keyword [1 ], source .keyword [2 ] },
269+ }
270+ end
271+ end
272+
273+ local function buildSource (source , sub , used , symbols )
239274 if source .type == ' local'
240275 or source .type == ' setlocal'
241276 or source .type == ' setglobal'
@@ -244,26 +279,32 @@ local function buildSource(source, text, used, symbols)
244279 or source .type == ' tablefield'
245280 or source .type == ' tableexp'
246281 or source .type == ' tableindex' then
247- buildValue (source , text , used , symbols )
282+ buildValue (source , sub , used , symbols )
248283 elseif source .type == ' function' then
249- buildAnonymousFunction (source , text , used , symbols )
284+ buildAnonymousFunction (source , sub , used , symbols )
285+ elseif source .type == ' if'
286+ or source .type == ' while'
287+ or source .type == ' in'
288+ or source .type == ' loop'
289+ or source .type == ' repeat' then
290+ buildBlock (source , sub , used , symbols )
250291 end
251292end
252293
253294--- @async
254295local function makeSymbol (uri )
255- local ast = files .getState (uri )
256- local text = files .getText (uri )
257- if not ast or not text then
296+ local state = files .getState (uri )
297+ if not state then
258298 return nil
259299 end
260300
301+ local sub = subber (state )
261302 local symbols = {}
262303 local used = {}
263304 local i = 0
264305 --- @async
265- guide .eachSource (ast .ast , function (source )
266- buildSource (source , text , used , symbols )
306+ guide .eachSource (state .ast , function (source )
307+ buildSource (source , sub , used , symbols )
267308 i = i + 1
268309 if i % 1000 == 0 then
269310 await .delay ()
0 commit comments