Когда-то писал подобное... Так что голосую за kashperuk

Что хочется отметить:
1. Не хвататет для полного счастья макросов и методов класса Global:
X++:
if (selectedLine)
{
//The main elementTypes - can be extended
add2Set(#ExtendedDataTypesPath);
add2Set(#BaseEnumsPath);
add2Set(#TablesPath);
add2Set(#ClassesPath);
add2Set(#FormsPath);
add2Set(#ReportsPath);
add2Set(#MacrosPath); // Macros
//if nothing was found in the AOT, we'll try searching in systemDocumentation
if (selectedNodesSet.elements() == 0)
{
add2Set(#SystemFunctionsPath);
add2Set(#SystemTablesPath);
add2Set(#SystemTypesPath);
add2Set(#SystemEnumsPath);
add2Set(#SystemClassesPath);
add2Set(#ClassesPath + #AOTRootPath + classstr(Global)); // Global
}
2. Формы и отчеты - не нужны - только сбивают с толку. Если этим скриптом пользоваться из кода, то нельзя объявить переменную типа названия формы. В то же время может существовать таблица/класс/едт который совпадает с названием формы. А значит скрипт откроет лишние окна. В случае макросов - по идее тоже можно провести анализ на наличие перед названием - символа # или фразы GlobalMacro - но для простоты так делать не хочется
3. Открываются сразу 2 окна (в случае системной доки) - одно окно узла и другое - окно редактора. Окно узла - лишнее - его вполне можно убрать - сделав в коде анализ типа узла. Также вылезает окно свойств - что как мне кажется только мешает. Хотя как говорится на вкус и цвет товарищей нет.
В общем - это пока только те вещи, которые можно убрать из кода (если конечно доберусь - то исправлю - а если нет (что скорее всего) - то пусть останутся просто моим мнением)
4. Что еще можно сделать (автор идеи - db) - это построить по узлу, который открыт в редакторе перекрестные ссылки (табл TmpxRefReferences и класс xRefCreate) и делать тоже самое - только выделяя переменные, а не сами названия узлов АОТ
5. Ну и в заключение - можно еще искать контролы на форме/отчете с AutoDeclaration=Yes. Для этого нужно убедиться, что редактор открыт у формы/отчета и путем перебора дерева контролов можно найти сей контрол.
Код у меня он оформлен как 2 вспомогательных метода, что с ходу не впишется в представленный скрипт. Однако идею можно переработать.
X++:
// _sourceNode = '\\Forms\\Address' (к примеру), получается через TreeNode::findNode(e.path()).AOTParent().TreeNodePath()
// _declaration - тоже самое что и selectedLine
public TreeNode findControlNode(TreeNode _sourceNode, str _declaration)
{
TreeNode declTreeNode;
TreeNode ret;
int i;
str s;
#AOT
;
i = strfind(_sourceNode.treeNodePath(), '\\', strlen(#AOTRootPath) + 1, strlen(_sourceNode.treeNodePath()));
if (i < 1)
{
return ret;
}
s = substr(_sourceNode.treeNodePath(), 1, i - 1);
i = strfind(_sourceNode.treeNodePath(), '\\', strlen(s) + 2, strlen(_sourceNode.treeNodePath()));
switch (s)
{
case #FormsPath, #ReportsPath:
s = substr(_sourceNode.treeNodePath() + '\\Designs', 1, i - 1);
ret = this.findSubNode(TreeNode::findNode(s), _declaration);
break;
default:
}
return ret;
}
Код функции findSubNode
X++:
private TreeNode findSubNode(TreeNode _startNode, TreeNodeName _nodeName, TreeNode _parentNode = null)
{
int i;
TreeNode curNode, subNode;
TreeNodeIterator it;
TreeNodePath subNodePath;
;
curNode = _parentNode ? _parentNode : _startNode;
it = curNode.AOTiterator();
subNode = it.next();
while (subNode)
{
subNodePath = subNode.treeNodePath();
if (this.isNodeOk(subNode, _nodeName))
{
break;
}
if (subNode.AOTchildNodeCount() > 0)
{
subNode = this.findSubNode(_startNode, _nodeName, subNode);
subNodePath = '';
if (subNode)
{
subNodePath = subNode.treeNodePath();
}
}
if (this.isNodeOk(subNode, _nodeName))
{
break;
}
else
{
subNode = it.next();
subNodePath = '';
}
}
return subNode;
}