-
Notifications
You must be signed in to change notification settings - Fork 146
/
Copy pathtodoall.lua
207 lines (178 loc) · 6.04 KB
/
todoall.lua
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
-- Copyright 2017 Paul Kulchenko, ZeroBrane LLC; All rights reserved
-- Contributed by Chronos Phaenon Eosphoros (@cpeosphoros)
-- Some code taken from those plugins:
-- todo.lua:
-- Copyright 2014 Paul Kulchenko, ZeroBrane LLC; All rights reserved
-- Contributed by Mark Fainstein
-- analyzeall.lua:
-- Copyright 2014 Paul Kulchenko, ZeroBrane LLC; All rights reserved
local id = ID("TODOAllpanel.referenceview")
local TODOpanel = "TODOAllpanel"
local refeditor
local spec = {iscomment = {}}
local function path2mask(s)
return s
:gsub('([%(%)%.%%%+%-%?%[%^%$%]])','%%%1') -- escape all special symbols
:gsub("%*", ".*") -- but expand asterisk into sequence of any symbols
:gsub("[\\/]","[\\\\/]") -- allow for any path
end
local fileTasks
local function mapTODOS(fileName, text)
local i = 0
local tasks = {}
while true do
--find next todo index
i = string.find(text, "TODO:", i+1)
if i == nil then
fileTasks[fileName] = tasks
break
end
local j = string.find(text, "\n",i+1)
local taskStr = string.sub(text, i+5, j)
table.insert(tasks, {pos = i, str = taskStr})
end
end
local function readfile(filePath)
local input = io.open(filePath)
local data = input:read("*a")
input:close()
return data
end
local function sortedKeys(tbl)
local sorted = {}
for k, _ in pairs (tbl) do
table.insert(sorted, k)
end
table.sort(sorted)
return sorted
end
local projectPath
local function fileNameFromPath(filePath)
return filePath:gsub(projectPath, "")
end
local function mapProject(self, editor)
local specs = self:GetConfig().ignore or {}
if editor then
mapTODOS(fileNameFromPath(ide:GetDocument(editor):GetFilePath()), editor:GetText())
else
local masks = {}
for i in ipairs(specs) do masks[i] = "^"..path2mask(specs[i]).."$" end
for _, filePath in ipairs(ide:GetFileList(projectPath, true, "*.lua")) do
local fileName = fileNameFromPath(filePath)
local ignore = false or editor
for _, spec in ipairs(masks) do
ignore = ignore or fileName:find(spec)
end
-- TODO: testing here
if not ignore then
mapTODOS(fileName, readfile(filePath))
end
end
end
local files = sortedKeys(fileTasks)
local tasksListStr = "Tasks List: \n\n"
local lineCounter = 2
local positions = {}
local function insertLine(line, pos, file)
tasksListStr = tasksListStr .. line
lineCounter = lineCounter + 1
if pos then
positions[lineCounter] = {pos = pos, file = file}
end
end
for _, file in ipairs(files) do
local tasks = fileTasks[file]
if tasks and #tasks ~= 0 then
insertLine(file .. ":\n", 1, file)
for counter, taskStr in ipairs(tasks) do
insertLine(counter.."."..taskStr.str, taskStr.pos, file)
end
insertLine("\n")
end
end
refeditor:SetReadOnly(false)
refeditor:SetText(tasksListStr)
refeditor:SetReadOnly(true)
--On click of a task, go to relevant position in the text
refeditor:Connect(wxstc.wxEVT_STC_DOUBLECLICK, function()
local line = refeditor:GetCurrentLine()+1
local position = positions[line]
if not position then return end
local filePath = projectPath .. position.file
local docs = ide:GetDocuments()
local editor
for _, doc in ipairs(docs) do
if doc:GetFilePath() == filePath then
editor = doc:GetEditor()
break
end
end
if not editor then
editor = ide:LoadFile(filePath)
if not editor then error("Couldn't load " .. filePath) end
end
editor:GotoPosEnforcePolicy(position.pos - 1)
if not ide:GetEditorWithFocus(editor) then ide:GetDocument(editor):SetActive() end
end)
end
return {
name = "Show project-wide TODO panel",
description = "Adds a project-wide panel for showing a tasks list.",
author = "Chronos Phaenon Eosphoros",
version = 0.13,
dependencies = "1.60",
onRegister = function(self)
local e = ide:CreateBareEditor()
refeditor = e
local w, h = 250, 250
local conf = function(pane)
pane:Dock():MinSize(w,-1):BestSize(w,-1):FloatingSize(w,h)
end
local layout = ide:GetSetting("/view", "uimgrlayout")
--if ide:IsPanelDocked(TODOpanel) then
if not layout or not layout:find(TODOpanel) then
ide:AddPanelDocked(ide.frame.projnotebook, e, TODOpanel, TR("PTasks"), conf)
else
ide:AddPanel(e, TODOpanel, TR("Tasks"), conf)
end
do -- markup handling in the reference panel
-- copy some settings from the lua spec
for _, s in ipairs({'lexer', 'lexerstyleconvert'}) do
spec[s] = ide.specs.lua[s]
end
-- this allows the markup to be recognized in all token types
for i = 0, 16 do spec.iscomment[i] = true end
e:Connect(wxstc.wxEVT_STC_UPDATEUI, function() MarkupStyle(e,0,e:GetLineCount()) end)
end
e:SetReadOnly(true)
e:SetWrapMode(wxstc.wxSTC_WRAP_NONE)
e:SetupKeywords("lua",spec,ide:GetConfig().styles,ide:GetOutput():GetFont())
-- remove all margins
for m = 0, 4 do e:SetMarginWidth(m, 0) end
-- disable dragging to the panel
e:Connect(wxstc.wxEVT_STC_DO_DROP, function(event) event:SetDragResult(wx.wxDragNone) end)
local menu = ide:GetMenuBar():GetMenu(ide:GetMenuBar():FindMenu(TR("&Project")))
menu:InsertCheckItem(4, id, TR("Tasks List")..KSC(id))
menu:Connect(id, wx.wxEVT_COMMAND_MENU_SELECTED, function ()
local uimgr = ide:GetUIManager()
uimgr:GetPane(TODOpanel):Show(not uimgr:GetPane(TODOpanel):IsShown())
uimgr:Update()
end)
ide:GetMainFrame():Connect(id, wx.wxEVT_UPDATE_UI, function (event)
local pane = ide:GetUIManager():GetPane(TODOpanel)
menu:Enable(event:GetId(), pane:IsOk()) -- disable if doesn't exist
menu:Check(event:GetId(), pane:IsOk() and pane:IsShown())
end)
end,
onUnRegister = function(self)
ide:RemoveMenuItem(id)
end,
onProjectLoad = function(self, project)
fileTasks = {}
projectPath = project
mapProject(self)
end,
onEditorCharAdded = function(self, editor) --, event)
mapProject(self, editor)
end,
}