Description:
Class browser does not show classes when short class declaration is used
type
TControlM = class(TControl);
TCustomGroupBoxM = class(TCustomGroupBox);
TFrameBaseDS = class(TFrameBase)
end;
Class browser tree:
(...)
TFrameBase
-- TControlM.TCustomGroupBoxM.TFrameBaseDS
there is no expected element
TFrameBase
-- TFrameBaseDS
Bug Details:
The bug is reproducible 100% of the time
Steps:
(by CLAUDE.AI, Sonnet 4.6):
Bug fix: Class Browser incorrectly nests classes that follow short class declarations
Problem
When a Pascal unit contains "short" (empty-body) class declarations immediately before a full class declaration, the Class Browser displays the full class with a concatenated name instead of showing it as a standalone entry.
Example source:
Expected tree:
TFrameBase
-- TFrameBaseDS
Actual (buggy) tree:
TFrameBase
-- TControlM.TCustomGroupBoxM.TFrameBaseDS
Root cause
FindClassEndIndexin GX_ClassMgr.pas is used byDetectNestingto locate the closing end token for each class declaration. It scans forward from the class identifier and tracks nesting depth by counting class/end pairs.When called for
TControlM = class(TControl);, it encountered class( and incremented the depth counter, expecting a matching end. But short class declarations have no body and no end, so the depth counter was never decremented back to zero. The function continued scanning into subsequent declarations, eventually finding the end ofTFrameBaseDSand returning it as the "end" ofTControlM.As a result,
DetectNestingpushedTControlMonto the nesting stack, thenTCustomGroupBoxM(similarly affected), and finally nestedTFrameBaseDSinside both of them — producing theTControlM.TCustomGroupBoxM.TFrameBaseDSname.Fix
Two changes were made to
FindClassEndIndexin Source/Framework/GX_ClassMgr.pas:Early exit at function entry. Before the main scanning loop, the function now checks whether the class identified by
IdentIndexis itself a short declaration. It scans forward to the class keyword, skips the optional ancestor list in parentheses, and checks if the next token is ;. If so, the function returns -1 immediately, correctly indicating that there is no matching end for this class.Short class detection in the main scan loop. When the main loop encounters a class keyword followed by (, it now skips to the matching ) and checks whether the next token is ;. If so, it treats this as a short class declaration (no body) and does not increment the depth counter. This handles the case of short class declarations appearing as nested types inside a full class body.
Thanks for the patch. I have applied it in a modified form in revision #5383
please retest.
Retested.
Works as expected.👍