dw_html.pp 85 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619262026212622262326242625262626272628262926302631263226332634263526362637263826392640264126422643264426452646264726482649265026512652265326542655265626572658265926602661266226632664266526662667266826692670267126722673267426752676267726782679268026812682268326842685268626872688268926902691269226932694269526962697269826992700270127022703270427052706270727082709271027112712271327142715271627172718271927202721272227232724272527262727272827292730273127322733273427352736273727382739274027412742274327442745274627472748274927502751275227532754275527562757275827592760276127622763276427652766276727682769277027712772277327742775277627772778277927802781278227832784278527862787278827892790279127922793279427952796279727982799280028012802280328042805280628072808280928102811281228132814281528162817281828192820282128222823282428252826282728282829283028312832283328342835283628372838283928402841284228432844284528462847284828492850285128522853285428552856285728582859286028612862286328642865286628672868286928702871287228732874287528762877287828792880288128822883288428852886288728882889289028912892289328942895289628972898289929002901290229032904290529062907290829092910291129122913291429152916291729182919292029212922292329242925292629272928292929302931293229332934293529362937293829392940294129422943294429452946294729482949295029512952295329542955295629572958295929602961296229632964296529662967296829692970297129722973297429752976297729782979298029812982298329842985298629872988298929902991299229932994299529962997
  1. {
  2. FPDoc - Free Pascal Documentation Tool
  3. Copyright (C) 2000 - 2005 by
  4. Areca Systems GmbH / Sebastian Guenther, [email protected]
  5. * HTML/XHTML output generator
  6. See the file COPYING, included in this distribution,
  7. for details about the copyright.
  8. This program is distributed in the hope that it will be useful,
  9. but WITHOUT ANY WARRANTY; without even the implied warranty of
  10. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  11. }
  12. {$mode objfpc}
  13. {$H+}
  14. unit dw_HTML;
  15. interface
  16. uses Classes, DOM, DOM_HTML, dGlobals, PasTree, dWriter;
  17. const
  18. // Subpage indices for modules
  19. ResstrSubindex = 1;
  20. ConstsSubindex = 2;
  21. TypesSubindex = 3;
  22. ClassesSubindex = 4;
  23. ProcsSubindex = 5;
  24. VarsSubindex = 6;
  25. // Maybe needed later for topic overview ??
  26. TopicsSubIndex = 7;
  27. // Subpage indices for classes
  28. PropertiesByInheritanceSubindex = 1;
  29. PropertiesByNameSubindex = 2;
  30. MethodsByInheritanceSubindex = 3;
  31. MethodsByNameSubindex = 4;
  32. EventsByInheritanceSubindex = 5;
  33. EventsByNameSubindex = 6;
  34. type
  35. TFileAllocator = class
  36. public
  37. procedure AllocFilename(AElement: TPasElement; ASubindex: Integer); virtual;
  38. function GetFilename(AElement: TPasElement;
  39. ASubindex: Integer): String; virtual; abstract;
  40. function GetRelativePathToTop(AElement: TPasElement): String; virtual;
  41. function GetCSSFilename(ARelativeTo: TPasElement): DOMString; virtual;
  42. end;
  43. TShortNameFileAllocator = class(TFileAllocator)
  44. private
  45. FExtension: String;
  46. public
  47. constructor Create(const AExtension: String);
  48. procedure AllocFilename(AElement: TPasElement; ASubindex: Integer); override;
  49. property Extension: String read FExtension;
  50. end;
  51. TLongNameFileAllocator = class(TFileAllocator)
  52. private
  53. FExtension: String;
  54. public
  55. constructor Create(const AExtension: String);
  56. function GetFilename(AElement: TPasElement;
  57. ASubindex: Integer): String; override;
  58. function GetRelativePathToTop(AElement: TPasElement): String; override;
  59. property Extension: String read FExtension;
  60. end;
  61. TPageInfo = class
  62. Element: TPasElement;
  63. SubpageIndex: Integer;
  64. end;
  65. { THTMLWriter }
  66. THTMLWriter = class(TFPDocWriter)
  67. private
  68. FOnTest: TNotifyEvent;
  69. FPackage: TPasPackage;
  70. function GetPageCount: Integer;
  71. procedure SetOnTest(const AValue: TNotifyEvent);
  72. protected
  73. FAllocator: TFileAllocator;
  74. Procedure CreateAllocator; virtual;
  75. CurDirectory: String; // relative to curdir of process
  76. BaseDirectory: String; // relative path to package base directory
  77. PageInfos: TObjectList; // list of TPageInfo objects
  78. Doc: THTMLDocument;
  79. BodyElement, TitleElement: TDOMElement;
  80. Module: TPasModule;
  81. OutputNodeStack: TList;
  82. CurOutputNode: TDOMNode;
  83. InsideHeadRow, DoPasHighlighting: Boolean;
  84. HighlighterFlags: Byte;
  85. FooterFile: string;
  86. function ResolveLinkID(const Name: String): DOMString;
  87. function ResolveLinkWithinPackage(AElement: TPasElement;
  88. ASubpageIndex: Integer): String;
  89. // Helper functions for creating DOM elements
  90. function CreateEl(Parent: TDOMNode; const AName: DOMString): THTMLElement;
  91. function CreatePara(Parent: TDOMNode): THTMLElement;
  92. function CreateH1(Parent: TDOMNode): THTMLElement;
  93. function CreateH2(Parent: TDOMNode): THTMLElement;
  94. function CreateH3(Parent: TDOMNode): THTMLElement;
  95. function CreateTable(Parent: TDOMNode): THTMLElement;
  96. function CreateContentTable(Parent: TDOMNode): THTMLElement;
  97. function CreateTR(Parent: TDOMNode): THTMLElement;
  98. function CreateTD(Parent: TDOMNode): THTMLElement;
  99. function CreateTD_vtop(Parent: TDOMNode): THTMLElement;
  100. function CreateLink(Parent: TDOMNode; const AHRef: DOMString): THTMLElement;
  101. function CreateAnchor(Parent: TDOMNode; const AName: DOMString): THTMLElement;
  102. function CreateCode(Parent: TDOMNode): THTMLElement;
  103. function CreateWarning(Parent: TDOMNode): THTMLElement;
  104. // Description node conversion
  105. procedure PushOutputNode(ANode: TDOMNode);
  106. procedure PopOutputNode;
  107. procedure DescrWriteText(const AText: DOMString); override;
  108. procedure DescrBeginBold; override;
  109. procedure DescrEndBold; override;
  110. procedure DescrBeginItalic; override;
  111. procedure DescrEndItalic; override;
  112. procedure DescrBeginEmph; override;
  113. procedure DescrEndEmph; override;
  114. procedure DescrWriteFileEl(const AText: DOMString); override;
  115. procedure DescrWriteKeywordEl(const AText: DOMString); override;
  116. procedure DescrWriteVarEl(const AText: DOMString); override;
  117. procedure DescrBeginLink(const AId: DOMString); override;
  118. procedure DescrEndLink; override;
  119. procedure DescrWriteLinebreak; override;
  120. procedure DescrBeginParagraph; override;
  121. procedure DescrEndParagraph; override;
  122. procedure DescrBeginCode(HasBorder: Boolean; const AHighlighterName: String); override;
  123. procedure DescrWriteCodeLine(const ALine: String); override;
  124. procedure DescrEndCode; override;
  125. procedure DescrBeginOrderedList; override;
  126. procedure DescrEndOrderedList; override;
  127. procedure DescrBeginUnorderedList; override;
  128. procedure DescrEndUnorderedList; override;
  129. procedure DescrBeginDefinitionList; override;
  130. procedure DescrEndDefinitionList; override;
  131. procedure DescrBeginListItem; override;
  132. procedure DescrEndListItem; override;
  133. procedure DescrBeginDefinitionTerm; override;
  134. procedure DescrEndDefinitionTerm; override;
  135. procedure DescrBeginDefinitionEntry; override;
  136. procedure DescrEndDefinitionEntry; override;
  137. procedure DescrBeginSectionTitle; override;
  138. procedure DescrBeginSectionBody; override;
  139. procedure DescrEndSection; override;
  140. procedure DescrBeginRemark; override;
  141. procedure DescrEndRemark; override;
  142. procedure DescrBeginTable(ColCount: Integer; HasBorder: Boolean); override;
  143. procedure DescrEndTable; override;
  144. procedure DescrBeginTableCaption; override;
  145. procedure DescrEndTableCaption; override;
  146. procedure DescrBeginTableHeadRow; override;
  147. procedure DescrEndTableHeadRow; override;
  148. procedure DescrBeginTableRow; override;
  149. procedure DescrEndTableRow; override;
  150. procedure DescrBeginTableCell; override;
  151. procedure DescrEndTableCell; override;
  152. procedure AppendText(Parent: TDOMNode; const AText: DOMString);
  153. procedure AppendNbSp(Parent: TDOMNode; ACount: Integer);
  154. procedure AppendSym(Parent: TDOMNode; const AText: DOMString);
  155. procedure AppendKw(Parent: TDOMNode; const AText: DOMString);
  156. function AppendPasSHFragment(Parent: TDOMNode; const AText: String;
  157. AShFlags: Byte): Byte;
  158. Procedure AppendShortDescr(AContext : TPasElement;Parent: TDOMNode; DocNode : TDocNode);
  159. procedure AppendShortDescr(Parent: TDOMNode; Element: TPasElement);
  160. procedure AppendDescr(AContext: TPasElement; Parent: TDOMNode;
  161. DescrNode: TDOMElement; AutoInsertBlock: Boolean);
  162. procedure AppendDescrSection(AContext: TPasElement; Parent: TDOMNode;
  163. DescrNode: TDOMElement; const ATitle: DOMString);
  164. procedure AppendShortDescrCell(Parent: TDOMNode; Element: TPasElement);
  165. function AppendHyperlink(Parent: TDOMNode; Element: TPasElement): TDOMElement;
  166. function AppendType(CodeEl, TableEl: TDOMElement;
  167. Element: TPasType; Expanded: Boolean;
  168. NestingLevel: Integer = 0): TDOMElement;
  169. function AppendProcType(CodeEl, TableEl: TDOMElement;
  170. Element: TPasProcedureType; Indent: Integer): TDOMElement;
  171. procedure AppendProcExt(CodeEl: TDOMElement; Element: TPasProcedure);
  172. procedure AppendProcDecl(CodeEl, TableEl: TDOMElement;
  173. Element: TPasProcedureBase);
  174. procedure AppendProcArgsSection(Parent: TDOMNode;
  175. Element: TPasProcedureType);
  176. function AppendRecordType(CodeEl, TableEl: TDOMElement;
  177. Element: TPasRecordType; NestingLevel: Integer): TDOMElement;
  178. procedure AppendTitle(const AText: DOMString);
  179. procedure AppendMenuBar(ASubpageIndex: Integer);
  180. procedure AppendTopicMenuBar(Topic : TTopicElement);
  181. procedure AppendSourceRef(AElement: TPasElement);
  182. procedure FinishElementPage(AElement: TPasElement);
  183. Procedure AppendSeeAlsoSection(AElement : TPasElement;DocNode : TDocNode);
  184. Procedure AppendExampleSection(AElement : TPasElement;DocNode : TDocNode);
  185. procedure AppendFooter;
  186. procedure CreatePageBody(AElement: TPasElement; ASubpageIndex: Integer); virtual;
  187. procedure CreatePackagePageBody;
  188. Procedure CreateTopicPageBody(AElement : TTopicElement);
  189. procedure CreateModulePageBody(AModule: TPasModule; ASubpageIndex: Integer);
  190. procedure CreateConstPageBody(AConst: TPasConst);
  191. procedure CreateTypePageBody(AType: TPasType);
  192. procedure CreateClassPageBody(AClass: TPasClassType; ASubpageIndex: Integer);
  193. procedure CreateClassMemberPageBody(AElement: TPasElement);
  194. procedure CreateVarPageBody(AVar: TPasVariable);
  195. procedure CreateProcPageBody(AProc: TPasProcedureBase);
  196. Procedure CreateTopicLinks(Node : TDocNode; PasElement : TPasElement);
  197. public
  198. constructor Create(APackage: TPasPackage; AEngine: TFPDocEngine); override;
  199. destructor Destroy; override;
  200. // Single-page generation
  201. function CreateHTMLPage(AElement: TPasElement;
  202. ASubpageIndex: Integer): TXMLDocument;
  203. function CreateXHTMLPage(AElement: TPasElement;
  204. ASubpageIndex: Integer): TXMLDocument;
  205. // For producing complete package documentation
  206. procedure WriteHTMLPages;
  207. procedure WriteXHTMLPages;
  208. SearchPage: String;
  209. property Allocator: TFileAllocator read FAllocator;
  210. property Package: TPasPackage read FPackage;
  211. property PageCount: Integer read GetPageCount;
  212. property OnTest: TNotifyEvent read FOnTest write SetOnTest;
  213. Function InterPretOption(Const Cmd,Arg : String) : boolean; override;
  214. Procedure WriteDoc; override;
  215. class procedure Usage(List: TStrings); override;
  216. end;
  217. THTMWriter = class(THTMLWriter)
  218. Protected
  219. Procedure CreateAllocator; override;
  220. end;
  221. implementation
  222. uses SysUtils, XHTML, XMLRead, XMLWrite, HTMWrite, sh_pas;
  223. Function FixHTMLpath(S : String) : STring;
  224. begin
  225. Result:=StringReplace(S,'\','/',[rfReplaceAll]);
  226. end;
  227. procedure TFileAllocator.AllocFilename(AElement: TPasElement;
  228. ASubindex: Integer);
  229. begin
  230. end;
  231. function TFileAllocator.GetRelativePathToTop(AElement: TPasElement): String;
  232. begin
  233. SetLength(Result, 0);
  234. end;
  235. function TFileAllocator.GetCSSFilename(ARelativeTo: TPasElement): DOMString;
  236. begin
  237. Result := GetRelativePathToTop(ARelativeTo) + 'fpdoc.css';
  238. end;
  239. constructor TShortNameFileAllocator.Create(const AExtension: String);
  240. begin
  241. inherited Create;
  242. FExtension := AExtension;
  243. end;
  244. procedure TShortNameFileAllocator.AllocFilename(AElement: TPasElement;
  245. ASubindex: Integer);
  246. begin
  247. // !!!: Add element to file list
  248. end;
  249. constructor TLongNameFileAllocator.Create(const AExtension: String);
  250. begin
  251. inherited Create;
  252. FExtension := AExtension;
  253. end;
  254. function TLongNameFileAllocator.GetFilename(AElement: TPasElement;
  255. ASubindex: Integer): String;
  256. var
  257. s: String;
  258. i: Integer;
  259. begin
  260. if AElement.ClassType = TPasPackage then
  261. Result := 'index'
  262. else if AElement.ClassType = TPasModule then
  263. Result := LowerCase(AElement.Name) + PathDelim + 'index'
  264. else
  265. begin
  266. if AElement is TPasOperator then
  267. begin
  268. Result := LowerCase(AElement.Parent.PathName) + '.op-';
  269. s := Copy(AElement.Name, Pos(' ', AElement.Name) + 1, Length(AElement.Name));
  270. s := Copy(s, 1, Pos('(', s) - 1);
  271. if s = ':=' then
  272. s := 'assign'
  273. else if s = '+' then
  274. s := 'add'
  275. else if s = '-' then
  276. s := 'sub'
  277. else if s = '*' then
  278. s := 'mul'
  279. else if s = '/' then
  280. s := 'div'
  281. else if s = '**' then
  282. s := 'power'
  283. else if s = '=' then
  284. s := 'equal'
  285. else if s = '<>' then
  286. s := 'unequal'
  287. else if s = '<' then
  288. s := 'less'
  289. else if s = '<=' then
  290. s := 'lessequal'
  291. else if s = '>' then
  292. s := 'greater'
  293. else if s = '>=' then
  294. s := 'greaterthan'
  295. else if s = '><' then
  296. s := 'symmetricdifference';
  297. Result := Result + s + '-';
  298. s := '';
  299. i := 1;
  300. while AElement.Name[i] <> '(' do
  301. Inc(i);
  302. Inc(i);
  303. while AElement.Name[i] <> ')' do
  304. begin
  305. if AElement.Name[i] = ',' then
  306. begin
  307. s := s + '-';
  308. Inc(i);
  309. end else
  310. s := s + AElement.Name[i];
  311. Inc(i);
  312. end;
  313. Result := Result + LowerCase(s) + '-' + LowerCase(Copy(AElement.Name,
  314. Pos('):', AElement.Name) + 3, Length(AElement.Name)));
  315. end else
  316. Result := LowerCase(AElement.PathName);
  317. i := 1;
  318. if (Length(Result) > 0) and (Result[1] = '#') then
  319. begin
  320. while Result[i] <> '.' do
  321. Inc(i);
  322. Result := Copy(Result, i + 1, Length(Result));
  323. end;
  324. i := 1;
  325. while (i <= Length(Result)) and (Result[i] <> '.') do
  326. Inc(i);
  327. if (i <= Length(Result)) and (i > 0) then
  328. Result[i] := PathDelim;
  329. end;
  330. if ASubindex > 0 then
  331. Result := Result + '-' + IntToStr(ASubindex);
  332. Result := Result + Extension;
  333. end;
  334. function TLongNameFileAllocator.GetRelativePathToTop(AElement: TPasElement): String;
  335. begin
  336. if (AElement.ClassType=TPasPackage) then
  337. Result := ''
  338. else if (AElement.ClassType=TTopicElement) then
  339. begin
  340. If (AElement.Parent.ClassType=TTopicElement) then
  341. Result:='../'+GetRelativePathToTop(AElement.Parent)
  342. else if (AElement.Parent.ClassType=TPasPackage) then
  343. Result:=''
  344. else if (AElement.Parent.ClassType=TPasModule) then
  345. Result:='../';
  346. end
  347. else
  348. Result := '../';
  349. end;
  350. constructor THTMLWriter.Create(APackage: TPasPackage; AEngine: TFPDocEngine);
  351. procedure AddPage(AElement: TPasElement; ASubpageIndex: Integer);
  352. var
  353. PageInfo: TPageInfo;
  354. begin
  355. PageInfo := TPageInfo.Create;
  356. PageInfo.Element := AElement;
  357. PageInfo.SubpageIndex := ASubpageIndex;
  358. PageInfos.Add(PageInfo);
  359. Allocator.AllocFilename(AElement, ASubpageIndex);
  360. if ASubpageIndex = 0 then
  361. Engine.AddLink(AElement.PathName,
  362. Allocator.GetFilename(AElement, ASubpageIndex));
  363. end;
  364. procedure AddTopicPages(AElement: TPasElement);
  365. var
  366. PreviousTopic,
  367. TopicElement : TTopicElement;
  368. PageInfo : TPageInfo;
  369. DocNode,
  370. TopicNode : TDocNode;
  371. begin
  372. DocNode:=Engine.FindDocNode(AElement);
  373. If not Assigned(DocNode) then
  374. exit;
  375. TopicNode:=DocNode.FirstChild;
  376. PreviousTopic:=Nil;
  377. While Assigned(TopicNode) do
  378. begin
  379. If TopicNode.TopicNode then
  380. begin
  381. TopicElement:=TTopicElement.Create(TopicNode.Name,AElement);
  382. Topics.Add(TopicElement);
  383. TopicElement.TopicNode:=TopicNode;
  384. TopicElement.Previous:=PreviousTopic;
  385. If Assigned(PreviousTopic) then
  386. PreviousTopic.Next:=TopicElement;
  387. PreviousTopic:=TopicElement;
  388. if AElement is TTopicElement then
  389. TTopicElement(AElement).SubTopics.Add(TopicElement);
  390. PageInfo := TPageInfo.Create;
  391. PageInfo.Element := TopicElement;
  392. PageInfo.SubpageIndex := 0;
  393. PageInfos.Add(PageInfo);
  394. Allocator.AllocFilename(TopicElement,0);
  395. Engine.AddLink(TopicElement.PathName, Allocator.GetFilename(TopicElement,0));
  396. if AElement is TTopicElement then
  397. TTopicElement(AElement).SubTopics.Add(TopicElement)
  398. else // Only one level of recursion.
  399. AddTopicPages(TopicElement);
  400. end;
  401. TopicNode:=TopicNode.NextSibling;
  402. end;
  403. end;
  404. procedure AddPages(AElement: TPasElement; ASubpageIndex: Integer;
  405. AList: TList);
  406. var
  407. i: Integer;
  408. begin
  409. if AList.Count > 0 then
  410. begin
  411. AddPage(AElement, ASubpageIndex);
  412. for i := 0 to AList.Count - 1 do
  413. AddPage(TPasElement(AList[i]), 0);
  414. end;
  415. end;
  416. procedure ScanModule(AModule: TPasModule);
  417. var
  418. i, j, k: Integer;
  419. s: String;
  420. ClassEl: TPasClassType;
  421. FPEl, AncestorMemberEl: TPasElement;
  422. DocNode: TDocNode;
  423. DidAutolink: Boolean;
  424. begin
  425. AddPage(AModule, 0);
  426. AddTopicPages(AModule);
  427. with AModule do
  428. begin
  429. if InterfaceSection.ResStrings.Count > 0 then
  430. begin
  431. AddPage(AModule, ResstrSubindex);
  432. s := Allocator.GetFilename(AModule, ResstrSubindex);
  433. for i := 0 to InterfaceSection.ResStrings.Count - 1 do
  434. with TPasResString(InterfaceSection.ResStrings[i]) do
  435. Engine.AddLink(PathName, s + '#' + LowerCase(Name));
  436. end;
  437. AddPages(AModule, ConstsSubindex, InterfaceSection.Consts);
  438. AddPages(AModule, TypesSubindex, InterfaceSection.Types);
  439. if InterfaceSection.Classes.Count > 0 then
  440. begin
  441. AddPage(AModule, ClassesSubindex);
  442. for i := 0 to InterfaceSection.Classes.Count - 1 do
  443. begin
  444. ClassEl := TPasClassType(InterfaceSection.Classes[i]);
  445. AddPage(ClassEl, 0);
  446. // !!!: Only add when there are items
  447. AddPage(ClassEl, PropertiesByInheritanceSubindex);
  448. AddPage(ClassEl, PropertiesByNameSubindex);
  449. AddPage(ClassEl, MethodsByInheritanceSubindex);
  450. AddPage(ClassEl, MethodsByNameSubindex);
  451. AddPage(ClassEl, EventsByInheritanceSubindex);
  452. AddPage(ClassEl, EventsByNameSubindex);
  453. for j := 0 to ClassEl.Members.Count - 1 do
  454. begin
  455. FPEl := TPasElement(ClassEl.Members[j]);
  456. if ((FPEl.Visibility = visPrivate) and Engine.HidePrivate) or
  457. ((FPEl.Visibility = visProtected) and Engine.HideProtected) then
  458. continue;
  459. DocNode := Engine.FindDocNode(FPEl);
  460. if not Assigned(DocNode) then
  461. begin
  462. DidAutolink := False;
  463. if Assigned(ClassEl.AncestorType) and
  464. (ClassEl.AncestorType.ClassType = TPasClassType) then
  465. begin
  466. for k := 0 to TPasClassType(ClassEl.AncestorType).Members.Count - 1 do
  467. begin
  468. AncestorMemberEl :=
  469. TPasElement(TPasClassType(ClassEl.AncestorType).Members[k]);
  470. if AncestorMemberEl.Name = FPEl.Name then
  471. begin
  472. DocNode := Engine.FindDocNode(AncestorMemberEl);
  473. if Assigned(DocNode) then
  474. begin
  475. DidAutolink := True;
  476. Engine.AddLink(FPEl.PathName,
  477. Engine.FindAbsoluteLink(AncestorMemberEl.PathName));
  478. break;
  479. end;
  480. end;
  481. end;
  482. end;
  483. if not DidAutolink then
  484. AddPage(FPEl, 0);
  485. end else
  486. AddPage(FPEl, 0);
  487. end;
  488. end;
  489. end;
  490. AddPages(AModule, ProcsSubindex, InterfaceSection.Functions);
  491. AddPages(AModule, VarsSubindex, InterfaceSection.Variables);
  492. end;
  493. end;
  494. var
  495. i: Integer;
  496. begin
  497. inherited ;
  498. CreateAllocator;
  499. FPackage := APackage;
  500. OutputNodeStack := TList.Create;
  501. PageInfos := TObjectList.Create;
  502. // Allocate page for the package itself, if a name is given (i.e. <> '#')
  503. if Length(Package.Name) > 1 then
  504. begin
  505. AddPage(Package, 0);
  506. AddTopicPages(Package);
  507. end;
  508. for i := 0 to Package.Modules.Count - 1 do
  509. ScanModule(TPasModule(Package.Modules[i]));
  510. end;
  511. destructor THTMLWriter.Destroy;
  512. begin
  513. PageInfos.Free;
  514. OutputNodeStack.Free;
  515. inherited Destroy;
  516. end;
  517. function THTMLWriter.CreateHTMLPage(AElement: TPasElement;
  518. ASubpageIndex: Integer): TXMLDocument;
  519. var
  520. HTMLEl: THTMLHtmlElement;
  521. HeadEl: THTMLHeadElement;
  522. El: TDOMElement;
  523. begin
  524. Doc := THTMLDocument.Create;
  525. Result := Doc;
  526. Doc.AppendChild(Doc.CreateProcessingInstruction(
  527. 'DOCTYPE', 'HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN"'));
  528. HTMLEl := Doc.CreateHtmlElement;
  529. Doc.AppendChild(HTMLEl);
  530. HeadEl := Doc.CreateHeadElement;
  531. HTMLEl.AppendChild(HeadEl);
  532. El := Doc.CreateElement('meta');
  533. HeadEl.AppendChild(El);
  534. El['http-equiv'] := 'Content-Type';
  535. El['content'] := 'text/html; charset=iso-8859-1';
  536. TitleElement := Doc.CreateElement('title');
  537. HeadEl.AppendChild(TitleElement);
  538. El := Doc.CreateElement('link');
  539. BodyElement := Doc.CreateElement('body');
  540. HTMLEl.AppendChild(BodyElement);
  541. CreatePageBody(AElement, ASubpageIndex);
  542. AppendFooter;
  543. HeadEl.AppendChild(El);
  544. El['rel'] := 'stylesheet';
  545. El['type'] := 'text/css';
  546. El['href'] := FixHtmlPath(Allocator.GetCSSFilename(AElement));
  547. end;
  548. function THTMLWriter.CreateXHTMLPage(AElement: TPasElement;
  549. ASubpageIndex: Integer): TXMLDocument;
  550. begin
  551. Result := nil;
  552. end;
  553. procedure CreatePath(const AFilename: String);
  554. var
  555. EndIndex: Integer;
  556. Path: String;
  557. begin
  558. EndIndex := Length(AFilename);
  559. if EndIndex = 0 then
  560. exit;
  561. while not (AFilename[EndIndex] in DirSeparators) do
  562. begin
  563. Dec(EndIndex);
  564. if EndIndex = 0 then
  565. exit;
  566. end;
  567. Path := Copy(AFilename, 1, EndIndex - 1);
  568. if not DirectoryExists(Path) then
  569. begin
  570. CreatePath(Path);
  571. MkDir(Path);
  572. end;
  573. end;
  574. procedure THTMLWriter.WriteHTMLPages;
  575. var
  576. i: Integer;
  577. PageDoc: TXMLDocument;
  578. Filename: String;
  579. begin
  580. if Engine.Output <> '' then
  581. Engine.Output := IncludeTrailingBackSlash(Engine.Output);
  582. for i := 0 to PageInfos.Count - 1 do
  583. with TPageInfo(PageInfos[i]) do
  584. begin
  585. PageDoc := CreateHTMLPage(Element, SubpageIndex);
  586. try
  587. Filename := Engine.Output + Allocator.GetFilename(Element, SubpageIndex);
  588. try
  589. CreatePath(Filename);
  590. WriteHTMLFile(PageDoc, Filename);
  591. except
  592. on E: Exception do
  593. WriteLn(Format(SErrCouldNotCreateFile, [FileName, e.Message]));
  594. end;
  595. finally
  596. PageDoc.Free;
  597. end;
  598. end;
  599. end;
  600. procedure THTMLWriter.WriteXHTMLPages;
  601. begin
  602. end;
  603. {procedure THTMLWriter.CreateDoc(const ATitle: DOMString;
  604. AElement: TPasElement; const AFilename: String);
  605. var
  606. El: TDOMElement;
  607. DocInfo: TDocInfo;
  608. CSSName: String;
  609. begin
  610. Doc := TXHTMLDocument.Create;
  611. with TXHTMLDocument(Doc) do
  612. begin
  613. Encoding := 'ISO8859-1';
  614. CSSName := 'fpdoc.css';
  615. if Assigned(Module) then
  616. CSSName := '../' + CSSName;
  617. $IFNDEF ver1_0
  618. StylesheetType := 'text/css';
  619. StylesheetHRef := CSSName;
  620. $ENDIF
  621. CreateRoot(xhtmlStrict);
  622. with RequestHeadElement do
  623. begin
  624. AppendText(RequestTitleElement, ATitle);
  625. El := CreateElement('link');
  626. AppendChild(El);
  627. El['rel'] := 'stylesheet';
  628. El['type'] := 'text/css';
  629. El['href'] := FixHtmlPath(CSSName);
  630. end;
  631. Self.BodyElement := RequestBodyElement('en');
  632. end;
  633. if Length(AFilename) > 0 then
  634. begin
  635. DocInfo := TDocInfo.Create;
  636. DocInfos.Add(DocInfo);
  637. DocInfo.Element := AElement;
  638. DocInfo.Filename := AFilename;
  639. end;
  640. end;
  641. }
  642. { Used for:
  643. - <link> elements in descriptions
  644. - "see also" entries
  645. - AppendHyperlink (for unresolved parse tree element links)
  646. }
  647. function THTMLWriter.ResolveLinkID(const Name: String): DOMString;
  648. var
  649. i: Integer;
  650. ThisPackage: TLinkNode;
  651. begin
  652. if Length(Name) = 0 then
  653. begin
  654. SetLength(Result, 0);
  655. exit;
  656. end;
  657. if Name[1] = '#' then
  658. Result := Engine.FindAbsoluteLink(Name)
  659. else
  660. begin
  661. SetLength(Result, 0);
  662. { Try all packages }
  663. ThisPackage := Engine.RootLinkNode.FirstChild;
  664. while Assigned(ThisPackage) do
  665. begin
  666. Result := Engine.FindAbsoluteLink(ThisPackage.Name + '.' + Name);
  667. if Length(Result) = 0 then
  668. begin
  669. if Assigned(Module) then
  670. Result := Engine.FindAbsoluteLink(Module.PathName + '.' + Name);
  671. // WriteLn('Searching for ', Module.PathName + '.' + Name, ' => ', Result);
  672. if Length(Result) = 0 then
  673. for i := Length(Name) downto 1 do
  674. if Name[i] = '.' then
  675. begin
  676. Result := ResolveLinkID(Copy(Name, 1, i - 1));
  677. exit;
  678. end;
  679. end;
  680. ThisPackage := ThisPackage.NextSibling;
  681. end;
  682. end;
  683. if Length(Result) > 0 then
  684. if Copy(Result, 1, Length(CurDirectory) + 1) = CurDirectory + '/' then
  685. Result := Copy(Result, Length(CurDirectory) + 2, Length(Result))
  686. else if not IsLinkAbsolute(Result) then
  687. Result := BaseDirectory + Result;
  688. end;
  689. function THTMLWriter.ResolveLinkWithinPackage(AElement: TPasElement;
  690. ASubpageIndex: Integer): String;
  691. var
  692. ParentEl: TPasElement;
  693. begin
  694. ParentEl := AElement;
  695. while Assigned(ParentEl) and not (ParentEl.ClassType = TPasPackage) do
  696. ParentEl := ParentEl.Parent;
  697. if Assigned(ParentEl) and (TPasPackage(ParentEl) = Engine.Package) then
  698. begin
  699. Result := Allocator.GetFilename(AElement, ASubpageIndex);
  700. if Copy(Result, 1, Length(CurDirectory) + 1) = CurDirectory + '/' then
  701. Result := Copy(Result, Length(CurDirectory) + 2, Length(Result))
  702. else
  703. Result := BaseDirectory + Result;
  704. end else
  705. SetLength(Result, 0);
  706. end;
  707. function THTMLWriter.CreateEl(Parent: TDOMNode;
  708. const AName: DOMString): THTMLElement;
  709. begin
  710. Result := Doc.CreateElement(AName);
  711. Parent.AppendChild(Result);
  712. end;
  713. function THTMLWriter.CreatePara(Parent: TDOMNode): THTMLElement;
  714. begin
  715. Result := CreateEl(Parent, 'p');
  716. end;
  717. function THTMLWriter.CreateH1(Parent: TDOMNode): THTMLElement;
  718. begin
  719. Result := CreateEl(Parent, 'h1');
  720. end;
  721. function THTMLWriter.CreateH2(Parent: TDOMNode): THTMLElement;
  722. begin
  723. Result := CreateEl(Parent, 'h2');
  724. end;
  725. function THTMLWriter.CreateH3(Parent: TDOMNode): THTMLElement;
  726. begin
  727. Result := CreateEl(Parent, 'h3');
  728. end;
  729. function THTMLWriter.CreateTable(Parent: TDOMNode): THTMLElement;
  730. begin
  731. Result := CreateEl(Parent, 'table');
  732. Result['cellspacing'] := '0';
  733. Result['cellpadding'] := '0';
  734. end;
  735. function THTMLWriter.CreateContentTable(Parent: TDOMNode): THTMLElement;
  736. begin
  737. Result := CreateEl(Parent, 'table');
  738. end;
  739. function THTMLWriter.CreateTR(Parent: TDOMNode): THTMLElement;
  740. begin
  741. Result := CreateEl(Parent, 'tr');
  742. end;
  743. function THTMLWriter.CreateTD(Parent: TDOMNode): THTMLElement;
  744. begin
  745. Result := CreateEl(Parent, 'td');
  746. end;
  747. function THTMLWriter.CreateTD_vtop(Parent: TDOMNode): THTMLElement;
  748. begin
  749. Result := CreateEl(Parent, 'td');
  750. Result['valign'] := 'top';
  751. end;
  752. function THTMLWriter.CreateLink(Parent: TDOMNode;
  753. const AHRef: DOMString): THTMLElement;
  754. begin
  755. Result := CreateEl(Parent, 'a');
  756. Result['href'] := FixHtmlPath(AHRef);
  757. end;
  758. function THTMLWriter.CreateAnchor(Parent: TDOMNode;
  759. const AName: DOMString): THTMLElement;
  760. begin
  761. Result := CreateEl(Parent, 'a');
  762. Result['name'] := AName;
  763. end;
  764. function THTMLWriter.CreateCode(Parent: TDOMNode): THTMLElement;
  765. begin
  766. Result := CreateEl(CreateEl(Parent, 'tt'), 'span');
  767. Result['class'] := 'code';
  768. end;
  769. function THTMLWriter.CreateWarning(Parent: TDOMNode): THTMLElement;
  770. begin
  771. Result := CreateEl(Parent, 'span');
  772. Result['class'] := 'warning';
  773. end;
  774. procedure THTMLWriter.PushOutputNode(ANode: TDOMNode);
  775. begin
  776. OutputNodeStack.Add(CurOutputNode);
  777. CurOutputNode := ANode;
  778. end;
  779. procedure THTMLWriter.PopOutputNode;
  780. begin
  781. CurOutputNode := TDOMNode(OutputNodeStack[OutputNodeStack.Count - 1]);
  782. OutputNodeStack.Delete(OutputNodeStack.Count - 1);
  783. end;
  784. procedure THTMLWriter.DescrWriteText(const AText: DOMString);
  785. begin
  786. AppendText(CurOutputNode, AText);
  787. end;
  788. procedure THTMLWriter.DescrBeginBold;
  789. begin
  790. PushOutputNode(CreateEl(CurOutputNode, 'b'));
  791. end;
  792. procedure THTMLWriter.DescrEndBold;
  793. begin
  794. PopOutputNode;
  795. end;
  796. procedure THTMLWriter.DescrBeginItalic;
  797. begin
  798. PushOutputNode(CreateEl(CurOutputNode, 'i'));
  799. end;
  800. procedure THTMLWriter.DescrEndItalic;
  801. begin
  802. PopOutputNode;
  803. end;
  804. procedure THTMLWriter.DescrBeginEmph;
  805. begin
  806. PushOutputNode(CreateEl(CurOutputNode, 'em'));
  807. end;
  808. procedure THTMLWriter.DescrEndEmph;
  809. begin
  810. PopOutputNode;
  811. end;
  812. procedure THTMLWriter.DescrWriteFileEl(const AText: DOMString);
  813. var
  814. NewEl: TDOMElement;
  815. begin
  816. NewEl := CreateEl(CurOutputNode, 'span');
  817. NewEl['class'] := 'file';
  818. AppendText(NewEl, AText);
  819. end;
  820. procedure THTMLWriter.DescrWriteKeywordEl(const AText: DOMString);
  821. var
  822. NewEl: TDOMElement;
  823. begin
  824. NewEl := CreateEl(CurOutputNode, 'span');
  825. NewEl['class'] := 'kw';
  826. AppendText(NewEl, AText);
  827. end;
  828. procedure THTMLWriter.DescrWriteVarEl(const AText: DOMString);
  829. begin
  830. AppendText(CreateEl(CurOutputNode, 'var'), AText);
  831. end;
  832. procedure THTMLWriter.DescrBeginLink(const AId: DOMString);
  833. var
  834. a,s: String;
  835. begin
  836. a:=AId;
  837. s := ResolveLinkID(a);
  838. if Length(s) = 0 then
  839. begin
  840. WriteLn(Format(SErrUnknownLinkID, [a]));
  841. PushOutputNode(CreateEl(CurOutputNode, 'b'));
  842. end else
  843. PushOutputNode(CreateLink(CurOutputNode, s));
  844. end;
  845. procedure THTMLWriter.DescrEndLink;
  846. begin
  847. PopOutputNode;
  848. end;
  849. procedure THTMLWriter.DescrWriteLinebreak;
  850. begin
  851. CreateEl(CurOutputNode, 'br');
  852. end;
  853. procedure THTMLWriter.DescrBeginParagraph;
  854. begin
  855. PushOutputNode(CreatePara(CurOutputNode));
  856. end;
  857. procedure THTMLWriter.DescrEndParagraph;
  858. begin
  859. PopOutputNode;
  860. end;
  861. procedure THTMLWriter.DescrBeginCode(HasBorder: Boolean; const AHighlighterName: String);
  862. begin
  863. DoPasHighlighting := (AHighlighterName = '') or (AHighlighterName = 'Pascal');
  864. HighlighterFlags := 0;
  865. PushOutputNode(CreateEl(CurOutputNode, 'pre'));
  866. end;
  867. procedure THTMLWriter.DescrWriteCodeLine(const ALine: String);
  868. begin
  869. if DoPasHighlighting then
  870. begin
  871. HighlighterFlags := AppendPasSHFragment(CurOutputNode, ALine,
  872. HighlighterFlags);
  873. AppendText(CurOutputNode, #10);
  874. end else
  875. AppendText(CurOutputNode, ALine + #10);
  876. end;
  877. procedure THTMLWriter.DescrEndCode;
  878. begin
  879. PopOutputNode;
  880. end;
  881. procedure THTMLWriter.DescrBeginOrderedList;
  882. begin
  883. PushOutputNode(CreateEl(CurOutputNode, 'ol'));
  884. end;
  885. procedure THTMLWriter.DescrEndOrderedList;
  886. begin
  887. PopOutputNode;
  888. end;
  889. procedure THTMLWriter.DescrBeginUnorderedList;
  890. begin
  891. PushOutputNode(CreateEl(CurOutputNode, 'ul'));
  892. end;
  893. procedure THTMLWriter.DescrEndUnorderedList;
  894. begin
  895. PopOutputNode;
  896. end;
  897. procedure THTMLWriter.DescrBeginDefinitionList;
  898. begin
  899. PushOutputNode(CreateEl(CurOutputNode, 'dl'));
  900. end;
  901. procedure THTMLWriter.DescrEndDefinitionList;
  902. begin
  903. PopOutputNode;
  904. end;
  905. procedure THTMLWriter.DescrBeginListItem;
  906. begin
  907. PushOutputNode(CreateEl(CurOutputNode, 'li'));
  908. end;
  909. procedure THTMLWriter.DescrEndListItem;
  910. begin
  911. PopOutputNode;
  912. end;
  913. procedure THTMLWriter.DescrBeginDefinitionTerm;
  914. begin
  915. PushOutputNode(CreateEl(CurOutputNode, 'dt'));
  916. end;
  917. procedure THTMLWriter.DescrEndDefinitionTerm;
  918. begin
  919. PopOutputNode;
  920. end;
  921. procedure THTMLWriter.DescrBeginDefinitionEntry;
  922. begin
  923. PushOutputNode(CreateEl(CurOutputNode, 'dd'));
  924. end;
  925. procedure THTMLWriter.DescrEndDefinitionEntry;
  926. begin
  927. PopOutputNode;
  928. end;
  929. procedure THTMLWriter.DescrBeginSectionTitle;
  930. begin
  931. PushOutputNode(CreateEl(CurOutputNode, 'h3'));
  932. end;
  933. procedure THTMLWriter.DescrBeginSectionBody;
  934. begin
  935. PopOutputNode;
  936. end;
  937. procedure THTMLWriter.DescrEndSection;
  938. begin
  939. end;
  940. procedure THTMLWriter.DescrBeginRemark;
  941. var
  942. NewEl, TDEl: TDOMElement;
  943. begin
  944. NewEl := CreateEl(CurOutputNode, 'table');
  945. NewEl['width'] := '100%';
  946. NewEl['border'] := '0';
  947. NewEl['CellSpacing'] := '0';
  948. NewEl['class'] := 'remark';
  949. NewEl := CreateTR(NewEl);
  950. TDEl := CreateTD(NewEl);
  951. TDEl['valign'] := 'top';
  952. TDEl['class'] := 'pre';
  953. AppendText(CreateEl(TDEl, 'b'), SDocRemark);
  954. PushOutputNode(CreateTD(NewEl));
  955. end;
  956. procedure THTMLWriter.DescrEndRemark;
  957. begin
  958. PopOutputNode;
  959. end;
  960. procedure THTMLWriter.DescrBeginTable(ColCount: Integer; HasBorder: Boolean);
  961. var
  962. Table: TDOMElement;
  963. begin
  964. Table := CreateEl(CurOutputNode, 'table');
  965. Table['border'] := IntToStr(Ord(HasBorder));
  966. PushOutputNode(Table);
  967. end;
  968. procedure THTMLWriter.DescrEndTable;
  969. begin
  970. PopOutputNode;
  971. end;
  972. procedure THTMLWriter.DescrBeginTableCaption;
  973. begin
  974. PushOutputNode(CreateEl(CurOutputNode, 'caption'));
  975. end;
  976. procedure THTMLWriter.DescrEndTableCaption;
  977. begin
  978. PopOutputNode;
  979. end;
  980. procedure THTMLWriter.DescrBeginTableHeadRow;
  981. begin
  982. PushOutputNode(CreateTr(CurOutputNode));
  983. InsideHeadRow := True;
  984. end;
  985. procedure THTMLWriter.DescrEndTableHeadRow;
  986. begin
  987. InsideHeadRow := False;
  988. PopOutputNode;
  989. end;
  990. procedure THTMLWriter.DescrBeginTableRow;
  991. begin
  992. PushOutputNode(CreateTR(CurOutputNode));
  993. end;
  994. procedure THTMLWriter.DescrEndTableRow;
  995. begin
  996. PopOutputNode;
  997. end;
  998. procedure THTMLWriter.DescrBeginTableCell;
  999. begin
  1000. if InsideHeadRow then
  1001. PushOutputNode(CreateEl(CurOutputNode, 'th'))
  1002. else
  1003. PushOutputNode(CreateTD(CurOutputNode));
  1004. end;
  1005. procedure THTMLWriter.DescrEndTableCell;
  1006. begin
  1007. PopOutputNode;
  1008. end;
  1009. procedure THTMLWriter.AppendText(Parent: TDOMNode; const AText: DOMString);
  1010. begin
  1011. Parent.AppendChild(Doc.CreateTextNode(AText));
  1012. end;
  1013. procedure THTMLWriter.AppendNbSp(Parent: TDOMNode; ACount: Integer);
  1014. begin
  1015. while ACount > 0 do
  1016. begin
  1017. Parent.AppendChild(Doc.CreateEntityReference('nbsp'));
  1018. Dec(ACount);
  1019. end;
  1020. end;
  1021. procedure THTMLWriter.AppendSym(Parent: TDOMNode; const AText: DOMString);
  1022. var
  1023. El: TDOMElement;
  1024. begin
  1025. El := CreateEl(Parent, 'span');
  1026. El['class'] := 'sym';
  1027. AppendText(El, AText);
  1028. end;
  1029. procedure THTMLWriter.AppendKw(Parent: TDOMNode; const AText: DOMString);
  1030. var
  1031. El: TDOMElement;
  1032. begin
  1033. El := CreateEl(Parent, 'span');
  1034. El['class'] := 'kw';
  1035. AppendText(El, AText);
  1036. end;
  1037. function THTMLWriter.AppendPasSHFragment(Parent: TDOMNode;
  1038. const AText: String; AShFlags: Byte): Byte;
  1039. var
  1040. Line, Last, p: PChar;
  1041. IsInSpecial: Boolean;
  1042. lastwasasm : boolean;
  1043. El: TDOMElement;
  1044. Procedure MaybeOutput;
  1045. Var
  1046. CurParent: TDomNode;
  1047. begin
  1048. If (Last<>Nil) then
  1049. begin
  1050. If (el<>Nil) then
  1051. CurParent:=El
  1052. else
  1053. CurParent:=Parent;
  1054. AppendText(CurParent,Last);
  1055. El:=Nil;
  1056. Last:=Nil;
  1057. end;
  1058. end;
  1059. Function NewEl(Const ElType,Attr,AttrVal : String) : TDomElement;
  1060. begin
  1061. Result:=CreateEl(Parent,ElType);
  1062. Result[Attr]:=AttrVal;
  1063. end;
  1064. Function NewSpan(Const AttrVal : String) : TDomElement;
  1065. begin
  1066. Result:=CreateEl(Parent,'span');
  1067. Result['class']:=AttrVal;
  1068. end;
  1069. begin
  1070. GetMem(Line, Length(AText) * 3 + 4);
  1071. Try
  1072. DoPascalHighlighting(AShFlags, PChar(AText), Line);
  1073. Result := AShFlags;
  1074. IsInSpecial := False;
  1075. Last := Nil;
  1076. p := Line;
  1077. el:=nil;
  1078. while p[0] <> #0 do
  1079. begin
  1080. if p[0] = LF_ESCAPE then
  1081. begin
  1082. p[0] := #0;
  1083. MaybeOutput;
  1084. case Ord(p[1]) of
  1085. shDefault: El:=Nil;
  1086. shInvalid: El:=newel('font','color','red');
  1087. shSymbol : El:=newspan('sym');
  1088. shKeyword: El:=newspan('kw');
  1089. shComment: El:=newspan('cmt');
  1090. shDirective: El:=newspan('dir');
  1091. shNumbers: El:=newspan('num');
  1092. shCharacters: El:=newspan('chr');
  1093. shStrings: El:=newspan('str');
  1094. shAssembler: El:=newspan('asm');
  1095. end;
  1096. Inc(P);
  1097. end
  1098. else If (Last=Nil) then
  1099. Last:=P;
  1100. Inc(p);
  1101. end;
  1102. MaybeOutput;
  1103. Finally
  1104. FreeMem(Line);
  1105. end;
  1106. end;
  1107. Procedure THTMLWriter.AppendShortDescr(AContext: TPasElement; Parent: TDOMNode; DocNode : TDocNode);
  1108. begin
  1109. if Assigned(DocNode) and Assigned(DocNode.ShortDescr) then
  1110. begin
  1111. PushOutputNode(Parent);
  1112. try
  1113. if not ConvertShort(AContext,TDomElement(DocNode.ShortDescr)) then
  1114. WriteLn(SErrInvalidShortDescr);
  1115. finally
  1116. PopOutputNode;
  1117. end;
  1118. end;
  1119. end;
  1120. procedure THTMLWriter.AppendShortDescr(Parent: TDOMNode; Element: TPasElement);
  1121. begin
  1122. AppendShortDescr(Element,Parent,Engine.FindDocNode(Element));
  1123. end;
  1124. procedure THTMLWriter.AppendDescr(AContext: TPasElement; Parent: TDOMNode;
  1125. DescrNode: TDOMElement; AutoInsertBlock: Boolean);
  1126. begin
  1127. if Assigned(DescrNode) then
  1128. begin
  1129. PushOutputNode(Parent);
  1130. try
  1131. ConvertDescr(AContext, DescrNode, AutoInsertBlock);
  1132. finally
  1133. PopOutputNode;
  1134. end;
  1135. end;
  1136. end;
  1137. procedure THTMLWriter.AppendDescrSection(AContext: TPasElement;
  1138. Parent: TDOMNode; DescrNode: TDOMElement; const ATitle: DOMString);
  1139. begin
  1140. if not IsDescrNodeEmpty(DescrNode) then
  1141. begin
  1142. If (ATitle<>'') then // Can be empty for topic.
  1143. AppendText(CreateH2(Parent), ATitle);
  1144. AppendDescr(AContext, Parent, DescrNode, True);
  1145. end;
  1146. end;
  1147. procedure THTMLWriter.AppendShortDescrCell(Parent: TDOMNode;
  1148. Element: TPasElement);
  1149. var
  1150. ParaEl: TDOMElement;
  1151. begin
  1152. if Assigned(Engine.FindShortDescr(Element)) then
  1153. begin
  1154. AppendNbSp(CreatePara(CreateTD(Parent)), 2);
  1155. ParaEl := CreatePara(CreateTD(Parent));
  1156. ParaEl['class'] := 'cmt';
  1157. AppendShortDescr(ParaEl, Element);
  1158. end;
  1159. end;
  1160. function THTMLWriter.AppendHyperlink(Parent: TDOMNode;
  1161. Element: TPasElement): TDOMElement;
  1162. var
  1163. s: String;
  1164. UnitList: TList;
  1165. i: Integer;
  1166. ThisPackage: TLinkNode;
  1167. begin
  1168. if Assigned(Element) then
  1169. begin
  1170. if Element.InheritsFrom(TPasUnresolvedTypeRef) then
  1171. begin
  1172. s := ResolveLinkID(Element.Name);
  1173. if Length(s) = 0 then
  1174. begin
  1175. { Try all packages }
  1176. ThisPackage := Engine.RootLinkNode.FirstChild;
  1177. while Assigned(ThisPackage) do
  1178. begin
  1179. s := ResolveLinkID(ThisPackage.Name + '.' + Element.Name);
  1180. if Length(s) > 0 then
  1181. break;
  1182. ThisPackage := ThisPackage.NextSibling;
  1183. end;
  1184. if Length(s) = 0 then
  1185. begin
  1186. { Okay, then we have to try all imported units of the current module }
  1187. UnitList := Module.InterfaceSection.UsesList;
  1188. for i := UnitList.Count - 1 downto 0 do
  1189. begin
  1190. { Try all packages }
  1191. ThisPackage := Engine.RootLinkNode.FirstChild;
  1192. while Assigned(ThisPackage) do
  1193. begin
  1194. s := ResolveLinkID(ThisPackage.Name + '.' +
  1195. TPasType(UnitList[i]).Name + '.' + Element.Name);
  1196. if Length(s) > 0 then
  1197. break;
  1198. ThisPackage := ThisPackage.NextSibling;
  1199. end;
  1200. if Length(s) > 0 then
  1201. break;
  1202. end;
  1203. end;
  1204. end;
  1205. end else
  1206. s := ResolveLinkID(Element.PathName);
  1207. if Length(s) > 0 then
  1208. begin
  1209. Result := CreateLink(Parent, s);
  1210. AppendText(Result, Element.Name);
  1211. end else
  1212. begin
  1213. Result := nil;
  1214. AppendText(Parent, Element.Name);
  1215. end;
  1216. end else
  1217. begin
  1218. Result := nil;
  1219. AppendText(CreateWarning(Parent), '<NIL>');
  1220. end;
  1221. end;
  1222. { Returns the new CodeEl, which will be the old CodeEl in most cases }
  1223. function THTMLWriter.AppendType(CodeEl, TableEl: TDOMElement;
  1224. Element: TPasType; Expanded: Boolean; NestingLevel: Integer): TDOMElement;
  1225. begin
  1226. Result := CodeEl;
  1227. if not Assigned(Element) then
  1228. AppendText(CreateWarning(CodeEl), '<NIL>')
  1229. else if (not Expanded) and (Length(Element.Name) > 0) then
  1230. AppendHyperlink(CodeEl, Element)
  1231. else
  1232. // Array
  1233. if Element.ClassType = TPasArrayType then
  1234. begin
  1235. AppendPasSHFragment(CodeEl,
  1236. 'array [' + TPasArrayType(Element).IndexRange + '] of ', 0);
  1237. Result := AppendType(CodeEl, TableEl, TPasArrayType(Element).ElType, False);
  1238. end else
  1239. // Procedure or funtion type
  1240. if Element.InheritsFrom(TPasProcedureType) then
  1241. begin
  1242. AppendKw(CodeEl, TPasProcedureType(Element).TypeName);
  1243. Result := AppendProcType(CodeEl, TableEl, TPasProcedureType(Element), 0)
  1244. end else
  1245. // Range type
  1246. if Element.InheritsFrom(TPasRangeType) then
  1247. AppendPasSHFragment(CodeEl, TPasRangeType(Element).RangeStart + '..' +
  1248. TPasRangeType(Element).RangeEnd, 0)
  1249. // Record type
  1250. else if Element.ClassType = TPasRecordType then
  1251. Result := AppendRecordType(CodeEl, TableEl, TPasRecordType(Element), NestingLevel)
  1252. else
  1253. // Other types
  1254. AppendHyperlink(CodeEl, Element);
  1255. end;
  1256. function THTMLWriter.AppendProcType(CodeEl, TableEl: TDOMElement;
  1257. Element: TPasProcedureType; Indent: Integer): TDOMElement;
  1258. function CreateIndentedCodeEl(Indent: Integer): TDOMElement;
  1259. begin
  1260. Result := CreateCode(CreatePara(CreateTD(CreateTR(TableEl))));
  1261. AppendNbSp(Result, Indent);
  1262. end;
  1263. var
  1264. i: Integer;
  1265. Arg: TPasArgument;
  1266. begin
  1267. if Element.Args.Count > 0 then
  1268. begin
  1269. AppendSym(CodeEl, '(');
  1270. for i := 0 to Element.Args.Count - 1 do
  1271. begin
  1272. Arg := TPasArgument(Element.Args[i]);
  1273. CodeEl := CreateIndentedCodeEl(Indent + 2);
  1274. case Arg.Access of
  1275. argConst: AppendKw(CodeEl, 'const ');
  1276. argVar: AppendKw(CodeEl, 'var ');
  1277. argOut: AppendKw(CodeEl, 'out ');
  1278. end;
  1279. AppendText(CodeEl, Arg.Name);
  1280. if Assigned(Arg.ArgType) then
  1281. begin
  1282. AppendSym(CodeEl, ': ');
  1283. CodeEl := AppendType(CodeEl, TableEl, Arg.ArgType, False);
  1284. end;
  1285. if Length(Arg.Value) > 0 then
  1286. AppendPasSHFragment(CodeEl, ' = ' + Arg.Value, 0);
  1287. if i < Element.Args.Count - 1 then
  1288. AppendSym(CodeEl, ';');
  1289. end;
  1290. if Element.InheritsFrom(TPasFunctionType) or Element.IsOfObject then
  1291. begin
  1292. CodeEl := CreateIndentedCodeEl(Indent);
  1293. if Element.InheritsFrom(TPasFunctionType) then
  1294. begin
  1295. AppendSym(CodeEl, '):');
  1296. AppendHyperlink(CodeEl, TPasFunctionType(Element).ResultEl.ResultType);
  1297. end else
  1298. AppendSym(CodeEl, ')');
  1299. if Element.IsOfObject then
  1300. begin
  1301. AppendText(CodeEl, ' '); // Don't remove
  1302. AppendKw(CodeEl, 'of object');
  1303. end;
  1304. end else
  1305. if Indent > 0 then
  1306. AppendSym(CodeEl, ')')
  1307. else
  1308. begin
  1309. CodeEl := CreateCode(CreatePara(CreateTD(CreateTR(TableEl))));
  1310. AppendSym(CodeEl, ')');
  1311. end;
  1312. end else
  1313. begin
  1314. { Procedure or function without arguments }
  1315. if Element.InheritsFrom(TPasFunctionType) then
  1316. begin
  1317. AppendSym(CodeEl, ': ');
  1318. AppendHyperlink(CodeEl, TPasFunctionType(Element).ResultEl.ResultType);
  1319. end;
  1320. if Element.IsOfObject then
  1321. AppendKw(CodeEl, ' of object');
  1322. end;
  1323. Result := CodeEl;
  1324. end;
  1325. procedure THTMLWriter.AppendProcExt(CodeEl: TDOMElement;
  1326. Element: TPasProcedure);
  1327. procedure AppendExt(const Ext: String);
  1328. begin
  1329. AppendKw(CodeEl, ' ' + Ext);
  1330. AppendSym(CodeEl, ';');
  1331. end;
  1332. begin
  1333. if Element.IsVirtual then
  1334. AppendExt('virtual');
  1335. if Element.IsDynamic then
  1336. AppendExt('dynamic');
  1337. if Element.IsAbstract then
  1338. AppendExt('abstract');
  1339. if Element.IsOverride then
  1340. AppendExt('override');
  1341. if Element.IsOverload then
  1342. AppendExt('overload');
  1343. if Element.IsMessage then
  1344. AppendExt('message');
  1345. end;
  1346. { Used in two places:
  1347. - Page for the method of a class
  1348. - Page for a tandalone procedure or function. }
  1349. procedure THTMLWriter.AppendProcDecl(CodeEl, TableEl: TDOMElement;
  1350. Element: TPasProcedureBase);
  1351. procedure WriteVariant(AProc: TPasProcedure);
  1352. begin
  1353. AppendProcArgsSection(TableEl.ParentNode, AProc.ProcType);
  1354. AppendKw(CodeEl, AProc.TypeName);
  1355. if Element.Parent.ClassType = TPasClassType then
  1356. begin
  1357. AppendText(CodeEl, ' ');
  1358. AppendHyperlink(CodeEl, Element.Parent);
  1359. AppendSym(CodeEl, '.');
  1360. AppendText(CodeEl, AProc.Name);
  1361. end else
  1362. AppendText(CodeEl, ' ' + AProc.FullName);
  1363. CodeEl := AppendProcType(CodeEl, TableEl, AProc.ProcType, 0);
  1364. AppendSym(CodeEl, ';');
  1365. AppendProcExt(CodeEl, AProc);
  1366. end;
  1367. var
  1368. i: Integer;
  1369. begin
  1370. if Element.ClassType = TPasOverloadedProc then
  1371. for i := 0 to TPasOverloadedProc(Element).Overloads.Count - 1 do
  1372. begin
  1373. if i > 0 then
  1374. begin
  1375. CreateEl(CodeEl, 'br');
  1376. CreateEl(CodeEl, 'br');
  1377. end;
  1378. WriteVariant(TPasProcedure(TPasOverloadedProc(Element).Overloads[i]));
  1379. end
  1380. else
  1381. WriteVariant(TPasProcedure(Element));
  1382. end;
  1383. procedure THTMLWriter.AppendProcArgsSection(Parent: TDOMNode;
  1384. Element: TPasProcedureType);
  1385. var
  1386. HasFullDescr, IsFirst: Boolean;
  1387. ResultEl: TPasResultElement;
  1388. ArgTableEl, TREl: TDOMElement;
  1389. DocNode: TDocNode;
  1390. i: Integer;
  1391. Arg: TPasArgument;
  1392. begin
  1393. IsFirst := True;
  1394. for i := 0 to Element.Args.Count - 1 do
  1395. begin
  1396. Arg := TPasArgument(Element.Args[i]);
  1397. if IsDescrNodeEmpty(Engine.FindShortDescr(Arg)) then
  1398. continue;
  1399. if IsFirst then
  1400. begin
  1401. IsFirst := False;
  1402. AppendText(CreateH2(Parent), SDocArguments);
  1403. ArgTableEl := CreateTable(Parent);
  1404. end;
  1405. TREl := CreateTR(ArgTableEl);
  1406. AppendText(CreateCode(CreatePara(CreateTD_vtop(TREl))), Arg.Name);
  1407. AppendShortDescrCell(TREl, Arg);
  1408. end;
  1409. if Element.ClassType = TPasFunctionType then
  1410. begin
  1411. ResultEl := TPasFunctionType(Element).ResultEl;
  1412. DocNode := Engine.FindDocNode(ResultEl);
  1413. HasFullDescr := Assigned(DocNode) and not IsDescrNodeEmpty(DocNode.Descr);
  1414. if HasFullDescr or
  1415. (Assigned(DocNode) and not IsDescrNodeEmpty(DocNode.ShortDescr)) then
  1416. begin
  1417. AppendText(CreateH2(Parent), SDocFunctionResult);
  1418. if HasFullDescr then
  1419. AppendDescr(ResultEl, Parent, DocNode.Descr, True)
  1420. else
  1421. AppendDescr(ResultEl, CreatePara(Parent), DocNode.ShortDescr, False);
  1422. end;
  1423. end;
  1424. end;
  1425. function THTMLWriter.AppendRecordType(CodeEl, TableEl: TDOMElement;
  1426. Element: TPasRecordType; NestingLevel: Integer): TDOMElement;
  1427. var
  1428. i, j: Integer;
  1429. Variable: TPasVariable;
  1430. TREl, TDEl: TDOMElement;
  1431. CurVariant: TPasVariant;
  1432. begin
  1433. if not (Element.Parent is TPasVariant) then
  1434. if Element.IsPacked then
  1435. AppendKw(CodeEl, 'packed record')
  1436. else
  1437. AppendKw(CodeEl, 'record');
  1438. for i := 0 to Element.Members.Count - 1 do
  1439. begin
  1440. Variable := TPasVariable(Element.Members[i]);
  1441. TREl := CreateTR(TableEl);
  1442. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  1443. AppendShortDescrCell(TREl, Variable);
  1444. AppendNbSp(CodeEl, NestingLevel * 2 + 2);
  1445. AppendText(CodeEl, Variable.Name);
  1446. AppendSym(CodeEl, ': ');
  1447. CodeEl := AppendType(CodeEl, TableEl, Variable.VarType, False, NestingLevel + 1);
  1448. AppendSym(CodeEl, ';');
  1449. end;
  1450. if Assigned(Element.VariantType) then
  1451. begin
  1452. TREl := CreateTR(TableEl);
  1453. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  1454. AppendNbSp(CodeEl, NestingLevel * 2 + 2);
  1455. AppendKw(CodeEl, 'case ');
  1456. if TPasRecordType(Element).VariantName <> '' then
  1457. begin
  1458. AppendText(CodeEl, TPasRecordType(Element).VariantName);
  1459. AppendSym(CodeEl, ': ');
  1460. end;
  1461. CodeEl := AppendType(CodeEl, TableEl, TPasRecordType(Element).VariantType, True);
  1462. AppendKw(CodeEl, ' of');
  1463. for i := 0 to TPasRecordType(Element).Variants.Count - 1 do
  1464. begin
  1465. CurVariant := TPasVariant(Element.Variants[i]);
  1466. TREl := CreateTR(TableEl);
  1467. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  1468. AppendNbSp(CodeEl, NestingLevel * 2 + 4);
  1469. for j := 0 to CurVariant.Values.Count - 1 do
  1470. begin
  1471. if j > 0 then
  1472. AppendSym(CodeEl, ', ');
  1473. AppendPasSHFragment(CodeEl, CurVariant.Values[j], 0);
  1474. end;
  1475. AppendSym(CodeEl, ': (');
  1476. AppendType(CodeEl, TableEl, CurVariant.Members, True, NestingLevel + 3);
  1477. CodeEl := CreateCode(CreatePara(CreateTD_vtop(CreateTR(TableEl))));
  1478. AppendNbSp(CodeEl, NestingLevel * 2 + 6);
  1479. AppendSym(CodeEl, ');');
  1480. end;
  1481. end;
  1482. if not (Element.Parent is TPasVariant) then
  1483. begin
  1484. CodeEl := CreateCode(CreatePara(CreateTD(CreateTR(TableEl))));
  1485. AppendText(CodeEl, ' '); // !!!: Dirty trick, necessary for current XML writer
  1486. AppendNbSp(CodeEl, NestingLevel * 2);
  1487. AppendKw(CodeEl, 'end');
  1488. end;
  1489. Result := CodeEl;
  1490. end;
  1491. procedure THTMLWriter.AppendTitle(const AText: DOMString);
  1492. begin
  1493. AppendText(TitleElement, AText);
  1494. AppendText(CreateH1(BodyElement), AText);
  1495. end;
  1496. procedure THTMLWriter.AppendTopicMenuBar(Topic : TTopicElement);
  1497. var
  1498. TableEl, TREl, ParaEl, TitleEl: TDOMElement;
  1499. procedure AddLink(El : TPasElement; const AName: String);
  1500. begin
  1501. AppendText(ParaEl, '[');
  1502. AppendText(CreateLink(ParaEl, ResolveLinkWithinPackage(El,0)),AName);
  1503. AppendText(ParaEl, ']');
  1504. end;
  1505. begin
  1506. TableEl := CreateEl(BodyElement, 'table');
  1507. TableEl['cellpadding'] := '4';
  1508. TableEl['cellspacing'] := '0';
  1509. TableEl['border'] := '0';
  1510. TableEl['width'] := '100%';
  1511. TableEl['class'] := 'bar';
  1512. TREl := CreateTR(TableEl);
  1513. ParaEl := CreateEl(CreateTD(TREl), 'b');
  1514. If Assigned(Topic.Previous) then
  1515. AddLink(Topic.Previous,SDocPrevious);
  1516. If Assigned(Topic.Parent) then
  1517. AddLink(Topic.Parent,SDocUp);
  1518. if Assigned(Topic.Next) then
  1519. AddLink(Topic.Next,SDocNext);
  1520. if Length(SearchPage) > 0 then
  1521. begin
  1522. AppendText(ParaEl, '[');
  1523. AppendText(CreateLink(ParaEl, SearchPage), SDocSearch);
  1524. AppendText(ParaEl, ']');
  1525. end;
  1526. ParaEl := CreateTD(TREl);
  1527. ParaEl['align'] := 'right';
  1528. TitleEl := CreateEl(ParaEl, 'span');
  1529. TitleEl['class'] := 'bartitle';
  1530. if Assigned(Module) then
  1531. AppendText(TitleEl, Format(SDocUnitTitle, [Module.Name]));
  1532. if Assigned(Package) then
  1533. begin
  1534. AppendText(TitleEl, ' (');
  1535. AppendHyperlink(TitleEl, Package);
  1536. AppendText(TitleEl, ')');
  1537. end;
  1538. end;
  1539. procedure THTMLWriter.AppendMenuBar(ASubpageIndex: Integer);
  1540. var
  1541. TableEl, TREl, ParaEl, TitleEl: TDOMElement;
  1542. procedure AddLink(ALinkSubpageIndex: Integer; const AName: String);
  1543. begin
  1544. AppendText(ParaEl, '[');
  1545. if ALinkSubpageIndex = ASubpageIndex then
  1546. AppendText(ParaEl, AName)
  1547. else
  1548. AppendText(
  1549. CreateLink(ParaEl, ResolveLinkWithinPackage(Module, ALinkSubpageIndex)),
  1550. AName);
  1551. AppendText(ParaEl, ']');
  1552. end;
  1553. begin
  1554. TableEl := CreateEl(BodyElement, 'table');
  1555. TableEl['cellpadding'] := '4';
  1556. TableEl['cellspacing'] := '0';
  1557. TableEl['border'] := '0';
  1558. TableEl['width'] := '100%';
  1559. TableEl['class'] := 'bar';
  1560. TREl := CreateTR(TableEl);
  1561. ParaEl := CreateEl(CreateTD(TREl), 'b');
  1562. if Assigned(Module) then
  1563. begin
  1564. AddLink(0, SDocOverview);
  1565. if Module.InterfaceSection.ResStrings.Count > 0 then
  1566. AddLink(ResstrSubindex, SDocResStrings);
  1567. if Module.InterfaceSection.Consts.Count > 0 then
  1568. AddLink(ConstsSubindex, SDocConstants);
  1569. if Module.InterfaceSection.Types.Count > 0 then
  1570. AddLink(TypesSubindex, SDocTypes);
  1571. if Module.InterfaceSection.Classes.Count > 0 then
  1572. AddLink(ClassesSubindex, SDocClasses);
  1573. if Module.InterfaceSection.Functions.Count > 0 then
  1574. AddLink(ProcsSubindex, SDocProceduresAndFunctions);
  1575. if Module.InterfaceSection.Variables.Count > 0 then
  1576. AddLink(VarsSubindex, SDocVariables);
  1577. end;
  1578. if Length(SearchPage) > 0 then
  1579. begin
  1580. AppendText(ParaEl, '[');
  1581. AppendText(CreateLink(ParaEl, SearchPage), SDocSearch);
  1582. AppendText(ParaEl, ']');
  1583. end;
  1584. ParaEl := CreateTD(TREl);
  1585. ParaEl['align'] := 'right';
  1586. TitleEl := CreateEl(ParaEl, 'span');
  1587. TitleEl['class'] := 'bartitle';
  1588. if Assigned(Module) then
  1589. AppendText(TitleEl, Format(SDocUnitTitle, [Module.Name]));
  1590. if Assigned(Package) then
  1591. begin
  1592. AppendText(TitleEl, ' (');
  1593. AppendHyperlink(TitleEl, Package);
  1594. AppendText(TitleEl, ')');
  1595. end;
  1596. end;
  1597. procedure THTMLWriter.AppendSourceRef(AElement: TPasElement);
  1598. begin
  1599. AppendText(CreatePara(BodyElement), Format(SDocSourcePosition,
  1600. [ExtractFileName(AElement.SourceFilename), AElement.SourceLinenumber]));
  1601. end;
  1602. Procedure THTMLWriter.AppendSeeAlsoSection(AElement : TPasElement;DocNode : TDocNode);
  1603. var
  1604. Node: TDOMNode;
  1605. TableEl, El, TREl, TDEl, ParaEl, NewEl, DescrEl: TDOMElement;
  1606. l,s: String;
  1607. f: Text;
  1608. IsFirstSeeAlso : Boolean;
  1609. begin
  1610. if Not (Assigned(DocNode) and Assigned(DocNode.SeeAlso)) then
  1611. Exit;
  1612. IsFirstSeeAlso := True;
  1613. Node:=DocNode.SeeAlso.FirstChild;
  1614. While Assigned(Node) do
  1615. begin
  1616. if (Node.NodeType=ELEMENT_NODE) and (Node.NodeName='link') then
  1617. begin
  1618. if IsFirstSeeAlso then
  1619. begin
  1620. IsFirstSeeAlso := False;
  1621. AppendText(CreateH2(BodyElement), SDocSeeAlso);
  1622. TableEl := CreateTable(BodyElement);
  1623. end;
  1624. El:=TDOMElement(Node);
  1625. TREl:=CreateTR(TableEl);
  1626. ParaEl:=CreatePara(CreateTD_vtop(TREl));
  1627. l:=El['id'];
  1628. s:= ResolveLinkID(l);
  1629. if Length(s)=0 then
  1630. begin
  1631. WriteLn(Format(SErrUnknownLinkID, [l]));
  1632. NewEl := CreateEl(ParaEl,'b')
  1633. end
  1634. else
  1635. NewEl := CreateLink(ParaEl,s);
  1636. if Not IsDescrNodeEmpty(El) then
  1637. begin
  1638. PushOutputNode(NewEl);
  1639. Try
  1640. ConvertBaseShortList(AElement, El, True)
  1641. Finally
  1642. PopOutputNode;
  1643. end;
  1644. end
  1645. else
  1646. AppendText(NewEl,El['id']);
  1647. l:=El['id'];
  1648. DescrEl := Engine.FindShortDescr(AElement.GetModule,L);
  1649. if Assigned(DescrEl) then
  1650. begin
  1651. AppendNbSp(CreatePara(CreateTD(TREl)), 2);
  1652. ParaEl := CreatePara(CreateTD(TREl));
  1653. ParaEl['class'] := 'cmt';
  1654. PushOutputNode(ParaEl);
  1655. try
  1656. ConvertShort(AElement, DescrEl);
  1657. finally
  1658. PopOutputNode;
  1659. end;
  1660. end;
  1661. end; // Link node
  1662. Node := Node.NextSibling;
  1663. end; // While
  1664. end;
  1665. Procedure THTMLWriter.AppendExampleSection(AElement : TPasElement;DocNode : TDocNode);
  1666. var
  1667. Node: TDOMNode;
  1668. // TableEl, El, TREl, TDEl, ParaEl, NewEl, DescrEl: TDOMElement;
  1669. s: String;
  1670. f: Text;
  1671. begin
  1672. if not (Assigned(DocNode) and Assigned(DocNode.FirstExample)) then
  1673. Exit;
  1674. Node := DocNode.FirstExample;
  1675. while Assigned(Node) do
  1676. begin
  1677. if (Node.NodeType = ELEMENT_NODE) and (Node.NodeName = 'example') then
  1678. begin
  1679. AppendText(CreateH2(BodyElement), SDocExample);
  1680. try
  1681. Assign(f, Engine.GetExampleFilename(TDOMElement(Node)));
  1682. Reset(f);
  1683. try
  1684. PushOutputNode(BodyElement);
  1685. DescrBeginCode(False, TDOMElement(Node)['highlighter']);
  1686. while not EOF(f) do
  1687. begin
  1688. ReadLn(f, s);
  1689. DescrWriteCodeLine(s);
  1690. end;
  1691. DescrEndCode;
  1692. PopOutputNode;
  1693. finally
  1694. Close(f);
  1695. end;
  1696. except
  1697. on e: Exception do
  1698. begin
  1699. e.Message := '[example] ' + e.Message;
  1700. raise;
  1701. end;
  1702. end;
  1703. end;
  1704. Node := Node.NextSibling;
  1705. end;
  1706. end;
  1707. procedure THTMLWriter.AppendFooter;
  1708. begin
  1709. if FooterFile<>'' then
  1710. ReadXMLFragment(BodyElement, FooterFile);
  1711. end;
  1712. procedure THTMLWriter.FinishElementPage(AElement: TPasElement);
  1713. var
  1714. DocNode: TDocNode;
  1715. begin
  1716. DocNode := Engine.FindDocNode(AElement);
  1717. If Assigned(DocNode) then
  1718. begin
  1719. // Description
  1720. if Assigned(DocNode.Descr) then
  1721. AppendDescrSection(AElement, BodyElement, DocNode.Descr, SDocDescription);
  1722. // Append "Errors" section
  1723. if Assigned(DocNode.ErrorsDoc) then
  1724. AppendDescrSection(AElement, BodyElement, DocNode.ErrorsDoc, SDocErrors);
  1725. // Append "See also" section
  1726. AppendSeeAlsoSection(AElement,DocNode);
  1727. // Append examples, if present
  1728. AppendExampleSection(AElement,DocNode);
  1729. end;
  1730. end;
  1731. Procedure THTMLWriter.CreateTopicPageBody(AElement : TTopicElement);
  1732. var
  1733. DocNode: TDocNode;
  1734. TableEl, TREl: TDOMElement;
  1735. I : Integer;
  1736. S : String;
  1737. begin
  1738. AppendTopicMenuBar(AElement);
  1739. DocNode:=AElement.TopicNode;
  1740. if Assigned(DocNode) then // should always be true, but we're being careful.
  1741. begin
  1742. AppendShortDescr(AElement,TitleElement, DocNode);
  1743. AppendShortDescr(AElement,CreateH2(BodyElement), DocNode);
  1744. if Assigned(DocNode.Descr) then
  1745. AppendDescrSection(AElement, BodyElement, DocNode.Descr, '');
  1746. AppendSeeAlsoSection(AElement,DocNode);
  1747. CreateTopicLinks(DocNode,AElement);
  1748. AppendExampleSection(AElement,DocNode);
  1749. end;
  1750. end;
  1751. procedure THTMLWriter.CreatePageBody(AElement: TPasElement;
  1752. ASubpageIndex: Integer);
  1753. var
  1754. i: Integer;
  1755. Element: TPasElement;
  1756. begin
  1757. CurDirectory := Allocator.GetFilename(AElement, ASubpageIndex);
  1758. i := Length(CurDirectory);
  1759. while (i > 0) and not (CurDirectory[i] in DirSeparators) do
  1760. Dec(i);
  1761. CurDirectory := Copy(CurDirectory, 1, i);
  1762. BaseDirectory := Allocator.GetRelativePathToTop(AElement);
  1763. if AElement.ClassType = TPasPackage then
  1764. CreatePackagePageBody
  1765. else
  1766. begin
  1767. Element := AElement;
  1768. while (Element<>Nil) and (Element.ClassType<>TPasModule) do
  1769. Element := Element.Parent;
  1770. Module := TPasModule(Element);
  1771. if AElement.ClassType = TPasModule then
  1772. CreateModulePageBody(TPasModule(AElement), ASubpageIndex)
  1773. else if AElement.Parent.InheritsFrom(TPasClassType) then
  1774. CreateClassMemberPageBody(AElement)
  1775. else if AElement.ClassType = TPasConst then
  1776. CreateConstPageBody(TPasConst(AElement))
  1777. else if AElement.InheritsFrom(TPasClassType) then
  1778. CreateClassPageBody(TPasClassType(AElement), ASubpageIndex)
  1779. else if AElement.InheritsFrom(TPasType) then
  1780. CreateTypePageBody(TPasType(AElement))
  1781. else if AElement.ClassType = TPasVariable then
  1782. CreateVarPageBody(TPasVariable(AElement))
  1783. else if AElement.InheritsFrom(TPasProcedureBase) then
  1784. CreateProcPageBody(TPasProcedure(AElement))
  1785. else if AElement.ClassType = TTopicELement then
  1786. CreateTopicPageBody(TTopicElement(AElement))
  1787. end;
  1788. end;
  1789. procedure THTMLWriter.CreatePackagePageBody;
  1790. var
  1791. DocNode: TDocNode;
  1792. TableEl, TREl: TDOMElement;
  1793. i: Integer;
  1794. ThisModule: TPasModule;
  1795. L : TStringList;
  1796. begin
  1797. AppendMenuBar(0);
  1798. AppendTitle(Format(SDocPackageTitle, [Copy(Package.Name, 2, 256)]));
  1799. AppendShortDescr(CreatePara(BodyElement), Package);
  1800. AppendText(CreateH2(BodyElement), SDocUnits);
  1801. TableEl := CreateTable(BodyElement);
  1802. L:=TStringList.Create;
  1803. Try
  1804. L.Sorted:=True;
  1805. // Sort modules.
  1806. For I:=0 to Package.Modules.Count-1 do
  1807. L.AddObject(TPasModule(Package.Modules[i]).Name,TPasModule(Package.Modules[i]));
  1808. // Now create table.
  1809. for i:=0 to L.Count - 1 do
  1810. begin
  1811. ThisModule := TPasModule(L.Objects[i]);
  1812. TREl := CreateTR(TableEl);
  1813. AppendHyperlink(CreateCode(CreatePara(CreateTD_vtop(TREl))), ThisModule);
  1814. AppendShortDescrCell(TREl, ThisModule);
  1815. end;
  1816. Finally
  1817. L.Free;
  1818. end;
  1819. DocNode := Engine.FindDocNode(Package);
  1820. if Assigned(DocNode) then
  1821. begin
  1822. if Assigned(DocNode.Descr) then
  1823. AppendDescrSection(nil, BodyElement, DocNode.Descr, SDocDescription);
  1824. CreateTopicLinks(DocNode,Package);
  1825. end;
  1826. end;
  1827. Procedure THTMLWriter.CreateTopicLinks(Node : TDocNode; PasElement : TPasElement);
  1828. var
  1829. DocNode: TDocNode;
  1830. TableEl, TREl: TDOMElement;
  1831. First : Boolean;
  1832. ThisTopic: TPasElement;
  1833. begin
  1834. DocNode:=Node.FirstChild;
  1835. First:=True;
  1836. While Assigned(DocNode) do
  1837. begin
  1838. If DocNode.TopicNode then
  1839. begin
  1840. if first then
  1841. begin
  1842. First:=False;
  1843. AppendText(CreateH2(BodyElement), SDocRelatedTopics);
  1844. TableEl := CreateTable(BodyElement);
  1845. end;
  1846. TREl := CreateTR(TableEl);
  1847. ThisTopic:=FindTopicElement(DocNode);
  1848. if Assigned(ThisTopic) then
  1849. AppendHyperlink(CreateCode(CreatePara(CreateTD_vtop(TREl))), ThisTopic);
  1850. AppendShortDescrCell(TREl, ThisTopic);
  1851. end;
  1852. DocNode:=DocNode.NextSibling;
  1853. end;
  1854. end;
  1855. procedure THTMLWriter.CreateModulePageBody(AModule: TPasModule;
  1856. ASubpageIndex: Integer);
  1857. procedure CreateMainPage;
  1858. var
  1859. TableEl, TREl, TDEl, CodeEl: TDOMElement;
  1860. i: Integer;
  1861. UnitRef: TPasType;
  1862. DocNode: TDocNode;
  1863. begin
  1864. AppendMenuBar(0);
  1865. AppendTitle(Format(SDocUnitTitle, [AModule.Name]));
  1866. AppendShortDescr(CreatePara(BodyElement), AModule);
  1867. if AModule.InterfaceSection.UsesList.Count > 0 then
  1868. begin
  1869. TableEl := CreateTable(BodyElement);
  1870. AppendKw(CreateCode(CreatePara(CreateTD(CreateTR(TableEl)))), 'uses');
  1871. for i := 0 to AModule.InterfaceSection.UsesList.Count - 1 do
  1872. begin
  1873. UnitRef := TPasType(AModule.InterfaceSection.UsesList[i]);
  1874. DocNode := Engine.FindDocNode(UnitRef);
  1875. if Assigned(DocNode) and DocNode.IsSkipped then
  1876. continue;
  1877. TREl := CreateTR(TableEl);
  1878. TDEl := CreateTD_vtop(TREl);
  1879. CodeEl := CreateCode(CreatePara(TDEl));
  1880. AppendNbSp(CodeEl, 2);
  1881. AppendHyperlink(CodeEl, UnitRef);
  1882. if i < AModule.InterfaceSection.UsesList.Count - 1 then
  1883. AppendSym(CodeEl, ',')
  1884. else
  1885. AppendSym(CodeEl, ';');
  1886. AppendText(CodeEl, ' '); // Space for descriptions
  1887. AppendShortDescrCell(TREl, UnitRef);
  1888. end;
  1889. end;
  1890. DocNode := Engine.FindDocNode(AModule);
  1891. if Assigned(DocNode) then
  1892. begin
  1893. if Assigned(DocNode.Descr) then
  1894. AppendDescrSection(AModule, BodyElement, DocNode.Descr, SDocOverview);
  1895. CreateTopicLinks(DocNode,AModule);
  1896. end;
  1897. end;
  1898. procedure CreateSimpleSubpage(const ATitle: DOMString; AList: TList);
  1899. var
  1900. TableEl, TREl, TDEl, CodeEl: TDOMElement;
  1901. i, j: Integer;
  1902. Decl: TPasElement;
  1903. SortedList: TList;
  1904. DocNode: TDocNode;
  1905. S : String;
  1906. begin
  1907. AppendMenuBar(ASubpageIndex);
  1908. S:=ATitle;
  1909. AppendTitle(Format(SDocUnitTitle + ': %s', [AModule.Name, S]));
  1910. SortedList := TList.Create;
  1911. try
  1912. for i := 0 to AList.Count - 1 do
  1913. begin
  1914. Decl := TPasElement(AList[i]);
  1915. DocNode := Engine.FindDocNode(Decl);
  1916. if (not Assigned(DocNode)) or (not DocNode.IsSkipped) then
  1917. begin
  1918. j := 0;
  1919. while (j < SortedList.Count) and (CompareText(
  1920. TPasElement(SortedList[j]).PathName, Decl.PathName) < 0) do
  1921. Inc(j);
  1922. SortedList.Insert(j, Decl);
  1923. end;
  1924. end;
  1925. TableEl := CreateTable(BodyElement);
  1926. for i := 0 to SortedList.Count - 1 do
  1927. begin
  1928. Decl := TPasElement(SortedList[i]);
  1929. TREl := CreateTR(TableEl);
  1930. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  1931. AppendHyperlink(CodeEl, Decl);
  1932. AppendShortDescrCell(TREl, Decl);
  1933. end;
  1934. finally
  1935. SortedList.Free;
  1936. end;
  1937. end;
  1938. procedure CreateResStringsPage;
  1939. var
  1940. ParaEl: TDOMElement;
  1941. i, j: Integer;
  1942. Decl: TPasResString;
  1943. DocNode: TDocNode;
  1944. begin
  1945. AppendMenuBar(ResstrSubindex);
  1946. AppendTitle(Format(SDocUnitTitle + ': %s', [AModule.Name, SDocResStrings]));
  1947. for i := 0 to AModule.InterfaceSection.ResStrings.Count - 1 do
  1948. begin
  1949. Decl := TPasResString(AModule.InterfaceSection.ResStrings[i]);
  1950. CreateEl(BodyElement, 'a')['name'] := LowerCase(Decl.Name);
  1951. ParaEl := CreatePara(BodyElement);
  1952. AppendText(CreateCode(ParaEl), Decl.Name);
  1953. CreateEl(ParaEl, 'br');
  1954. AppendText(ParaEl, Decl.Value);
  1955. end;
  1956. end;
  1957. begin
  1958. case ASubpageIndex of
  1959. 0:
  1960. CreateMainPage;
  1961. ResstrSubindex:
  1962. CreateResStringsPage;
  1963. ConstsSubindex:
  1964. CreateSimpleSubpage(SDocConstants, AModule.InterfaceSection.Consts);
  1965. TypesSubindex:
  1966. CreateSimpleSubpage(SDocTypes, AModule.InterfaceSection.Types);
  1967. ClassesSubindex:
  1968. CreateSimpleSubpage(SDocClasses, AModule.InterfaceSection.Classes);
  1969. ProcsSubindex:
  1970. CreateSimpleSubpage(SDocProceduresAndFunctions, AModule.InterfaceSection.Functions);
  1971. VarsSubindex:
  1972. CreateSimpleSubpage(SDocVariables, AModule.InterfaceSection.Variables);
  1973. end;
  1974. end;
  1975. procedure THTMLWriter.CreateConstPageBody(AConst: TPasConst);
  1976. var
  1977. TableEl, CodeEl: TDOMElement;
  1978. begin
  1979. AppendMenuBar(-1);
  1980. AppendTitle(AConst.Name);
  1981. AppendShortDescr(CreatePara(BodyElement), AConst);
  1982. AppendText(CreateH2(BodyElement), SDocDeclaration);
  1983. AppendSourceRef(AConst);
  1984. TableEl := CreateTable(BodyElement);
  1985. CodeEl := CreateCode(CreatePara(CreateTD(CreateTR(TableEl))));
  1986. AppendKw(CodeEl, 'const');
  1987. AppendText(CodeEl, ' ' + AConst.Name);
  1988. if Assigned(AConst.VarType) then
  1989. begin
  1990. AppendSym(CodeEl, ': ');
  1991. AppendType(CodeEl, TableEl, AConst.VarType, False);
  1992. end;
  1993. AppendPasSHFragment(CodeEl, ' = ' + AConst.Value + ';', 0);
  1994. FinishElementPage(AConst);
  1995. end;
  1996. procedure THTMLWriter.CreateTypePageBody(AType: TPasType);
  1997. var
  1998. TableEl, TREl, TDEl, CodeEl: TDOMElement;
  1999. DocNode: TDocNode;
  2000. i: Integer;
  2001. s: String;
  2002. EnumType: TPasEnumType;
  2003. EnumValue: TPasEnumValue;
  2004. Variable: TPasVariable;
  2005. begin
  2006. AppendMenuBar(-1);
  2007. AppendTitle(AType.Name);
  2008. AppendShortDescr(CreatePara(BodyElement), AType);
  2009. AppendText(CreateH2(BodyElement), SDocDeclaration);
  2010. AppendSourceRef(AType);
  2011. TableEl := CreateTable(BodyElement);
  2012. TREl := CreateTR(TableEl);
  2013. TDEl := CreateTD(TREl);
  2014. CodeEl := CreateCode(CreatePara(TDEl));
  2015. DocNode := Engine.FindDocNode(AType);
  2016. AppendKw(CodeEl, 'type ');
  2017. AppendText(CodeEl, AType.Name);
  2018. AppendSym(CodeEl, ' = ');
  2019. If Assigned(DocNode) and
  2020. Assigned(DocNode.Node) and
  2021. (Docnode.Node['opaque']='1') then
  2022. AppendText(CodeEl,SDocOpaque)
  2023. else
  2024. begin
  2025. // Alias
  2026. if AType.ClassType = TPasAliasType then
  2027. begin
  2028. if Assigned(TPasAliasType(AType).DestType) then
  2029. AppendHyperlink(CodeEl, TPasAliasType(AType).DestType)
  2030. else
  2031. AppendText(CreateWarning(CodeEl), '<Destination type is NIL>');
  2032. AppendSym(CodeEl, ';');
  2033. end else
  2034. // Class of
  2035. if AType.ClassType = TPasClassOfType then
  2036. begin
  2037. AppendKw(CodeEl, 'class of ');
  2038. AppendHyperlink(CodeEl, TPasClassOfType(AType).DestType);
  2039. AppendSym(CodeEl, ';');
  2040. end else
  2041. // Enumeration
  2042. if AType.ClassType = TPasEnumType then
  2043. begin
  2044. AppendSym(CodeEl, '(');
  2045. for i := 0 to TPasEnumType(AType).Values.Count - 1 do
  2046. begin
  2047. EnumValue := TPasEnumValue(TPasEnumType(AType).Values[i]);
  2048. TREl := CreateTR(TableEl);
  2049. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  2050. AppendShortDescrCell(TREl, EnumValue);
  2051. AppendNbSp(CodeEl, 2);
  2052. s := EnumValue.Name;
  2053. if EnumValue.IsValueUsed then
  2054. s := s + ' = ' + IntToStr(EnumValue.Value);
  2055. if i < TPasEnumType(AType).Values.Count - 1 then
  2056. s := s + ',';
  2057. AppendPasSHFragment(CodeEl, s, 0);
  2058. end;
  2059. AppendSym(CreateCode(CreatePara(CreateTD(CreateTR(TableEl)))), ');');
  2060. end else
  2061. // Pointer type
  2062. if AType.ClassType = TPasPointerType then
  2063. begin
  2064. AppendSym(CodeEl, '^');
  2065. if Assigned(TPasPointerType(AType).DestType) then
  2066. AppendHyperlink(CodeEl, TPasPointerType(AType).DestType)
  2067. else
  2068. AppendText(CreateWarning(CodeEl), '<Destination type is NIL>');
  2069. AppendSym(CodeEl, ';');
  2070. end else
  2071. if AType.InheritsFrom(TPasProcedureType) then
  2072. begin
  2073. AppendSym(AppendType(CodeEl, TableEl, TPasType(AType), True), ';');
  2074. AppendProcArgsSection(BodyElement, TPasProcedureType(AType));
  2075. end else
  2076. // Record
  2077. if AType.ClassType = TPasRecordType then
  2078. begin
  2079. CodeEl := AppendRecordType(CodeEl, TableEl, TPasRecordType(AType), 0);
  2080. AppendSym(CodeEl, ';');
  2081. end else
  2082. // Set
  2083. if AType.ClassType = TPasSetType then
  2084. begin
  2085. AppendKw(CodeEl, 'set of ');
  2086. if TPasSetType(AType).EnumType.ClassType = TPasEnumType then
  2087. begin
  2088. AppendSym(CodeEl, '(');
  2089. EnumType := TPasEnumType(TPasSetType(AType).EnumType);
  2090. for i := 0 to EnumType.Values.Count - 1 do
  2091. begin
  2092. EnumValue := TPasEnumValue(EnumType.Values[i]);
  2093. TREl := CreateTR(TableEl);
  2094. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  2095. AppendShortDescrCell(TREl, EnumValue);
  2096. AppendNbSp(CodeEl, 2);
  2097. s := EnumValue.Name;
  2098. if EnumValue.IsValueUsed then
  2099. s := s + ' = ' + IntToStr(EnumValue.Value);
  2100. if i < EnumType.Values.Count - 1 then
  2101. s := s + ',';
  2102. AppendPasSHFragment(CodeEl, s, 0);
  2103. end;
  2104. AppendSym(CreateCode(CreatePara(CreateTD(CreateTR(TableEl)))), ');');
  2105. end else
  2106. begin
  2107. AppendHyperlink(CodeEl, TPasSetType(AType).EnumType);
  2108. AppendSym(CodeEl, ';');
  2109. end;
  2110. end else
  2111. // Type alias
  2112. if AType.ClassType = TPasTypeAliasType then
  2113. begin
  2114. AppendKw(CodeEl, 'type ');
  2115. AppendHyperlink(CodeEl, TPasTypeAliasType(AType).DestType);
  2116. AppendSym(CodeEl, ';');
  2117. end else
  2118. // Probably one of the simple types, which allowed in other places as wel...
  2119. AppendSym(AppendType(CodeEl, TableEl, TPasType(AType), True), ';');
  2120. end;
  2121. FinishElementPage(AType);
  2122. end;
  2123. function PropertyFilter(AMember: TPasElement): Boolean;
  2124. begin
  2125. Result := (AMember.ClassType = TPasProperty) and
  2126. (Copy(AMember.Name, 1, 2) <> 'On');
  2127. end;
  2128. function MethodFilter(AMember: TPasElement): Boolean;
  2129. begin
  2130. Result := AMember.InheritsFrom(TPasProcedureBase);
  2131. end;
  2132. function EventFilter(AMember: TPasElement): Boolean;
  2133. begin
  2134. Result := (AMember.ClassType = TPasProperty) and
  2135. (Copy(AMember.Name, 1, 2) = 'On');
  2136. end;
  2137. procedure THTMLWriter.CreateClassPageBody(AClass: TPasClassType;
  2138. ASubpageIndex: Integer);
  2139. type
  2140. TMemberFilter = function(AMember: TPasElement): Boolean;
  2141. var
  2142. ParaEl: TDOMElement;
  2143. procedure AppendMemberListLink(AListSubpageIndex: Integer;
  2144. const AText: DOMString);
  2145. var
  2146. LinkEl: TDOMElement;
  2147. begin
  2148. AppendText(ParaEl, '[');
  2149. LinkEl := CreateEl(ParaEl, 'a');
  2150. LinkEl['href'] :=
  2151. FixHtmlPath(ResolveLinkWithinPackage(AClass, AListSubpageIndex));
  2152. LinkEl['onClick'] := 'window.open(''' + LinkEl['href'] + ''', ''list'', ' +
  2153. '''dependent=yes,resizable=yes,scrollbars=yes,height=400,width=300''); return false;';
  2154. AppendText(LinkEl, AText);
  2155. AppendText(ParaEl, ' (');
  2156. LinkEl := CreateEl(ParaEl, 'a');
  2157. LinkEl['href'] :=
  2158. FixHtmlPath(ResolveLinkWithinPackage(AClass, AListSubpageIndex + 1));
  2159. LinkEl['onClick'] := 'window.open(''' + LinkEl['href'] + ''', ''list'', ' +
  2160. '''dependent=yes,resizable=yes,scrollbars=yes,height=400,width=300''); return false;';
  2161. AppendText(LinkEl, SDocByName);
  2162. AppendText(ParaEl, ')');
  2163. AppendText(ParaEl, '] ');
  2164. end;
  2165. procedure CreateMainPage;
  2166. var
  2167. TableEl, TREl, TDEl, CodeEl: TDOMElement;
  2168. DocNode: TDocNode;
  2169. Member: TPasElement;
  2170. CurVisibility: TPasMemberVisibility;
  2171. i: Integer;
  2172. s: String;
  2173. ThisClass: TPasClassType;
  2174. HaveSeenTObject: Boolean;
  2175. begin
  2176. AppendMenuBar(-1);
  2177. AppendTitle(AClass.Name);
  2178. ParaEl := CreatePara(BodyElement);
  2179. AppendMemberListLink(PropertiesByInheritanceSubindex, SDocProperties);
  2180. AppendMemberListLink(MethodsByInheritanceSubindex, SDocMethods);
  2181. AppendMemberListLink(EventsByInheritanceSubindex, SDocEvents);
  2182. AppendShortDescr(CreatePara(BodyElement), AClass);
  2183. AppendText(CreateH2(BodyElement), SDocDeclaration);
  2184. AppendSourceRef(AClass);
  2185. TableEl := CreateTable(BodyElement);
  2186. TREl := CreateTR(TableEl);
  2187. TDEl := CreateTD(TREl);
  2188. CodeEl := CreateCode(CreatePara(TDEl));
  2189. AppendKw(CodeEl, 'type');
  2190. AppendText(CodeEl, ' ' + AClass.Name + ' ');
  2191. AppendSym(CodeEl, '=');
  2192. AppendText(CodeEl, ' ');
  2193. AppendKw(CodeEl, ObjKindNames[AClass.ObjKind]);
  2194. if Assigned(AClass.AncestorType) then
  2195. begin
  2196. AppendSym(CodeEl, '(');
  2197. AppendHyperlink(CodeEl, AClass.AncestorType);
  2198. AppendSym(CodeEl, ')');
  2199. end;
  2200. if AClass.Members.Count > 0 then
  2201. begin
  2202. CurVisibility := visDefault;
  2203. for i := 0 to AClass.Members.Count - 1 do
  2204. begin
  2205. Member := TPasElement(AClass.Members[i]);
  2206. if CurVisibility <> Member.Visibility then
  2207. begin
  2208. CurVisibility := Member.Visibility;
  2209. if ((CurVisibility = visPrivate) and Engine.HidePrivate) or
  2210. ((CurVisibility = visProtected) and Engine.HideProtected) then
  2211. continue;
  2212. case CurVisibility of
  2213. visPrivate: s := 'private';
  2214. visProtected: s := 'protected';
  2215. visPublic: s := 'public';
  2216. visPublished: s := 'published';
  2217. visAutomated: s := 'automated';
  2218. end;
  2219. AppendKw(CreateCode(CreatePara(CreateTD(CreateTR(TableEl)))), s);
  2220. end else
  2221. if ((CurVisibility = visPrivate) and Engine.HidePrivate) or
  2222. ((CurVisibility = visProtected) and Engine.HideProtected) then
  2223. continue;
  2224. TREl := CreateTR(TableEl);
  2225. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  2226. AppendNbSp(CodeEl, 2);
  2227. AppendShortDescrCell(TREl, Member);
  2228. if Member.InheritsFrom(TPasProcedureBase) then
  2229. begin
  2230. AppendKw(CodeEl, TPasProcedureBase(Member).TypeName + ' ');
  2231. AppendHyperlink(CodeEl, Member);
  2232. if (Member.ClassType = TPasOverloadedProc) or
  2233. (TPasProcedure(Member).ProcType.Args.Count > 0) then
  2234. AppendSym(CodeEl, '();')
  2235. else
  2236. AppendSym(CodeEl, ';');
  2237. if Member.ClassType <> TPasOverloadedProc then
  2238. AppendProcExt(CodeEl, TPasProcedure(Member));
  2239. end else
  2240. if Member.ClassType = TPasVariable then
  2241. begin
  2242. AppendHyperlink(CodeEl, Member);
  2243. AppendSym(CodeEl, ': ');
  2244. AppendHyperlink(CodeEl, TPasVariable(Member).VarType);
  2245. AppendSym(CodeEl, ';');
  2246. end else
  2247. if Member.ClassType = TPasProperty then
  2248. begin
  2249. AppendKw(CodeEl, 'property ');
  2250. AppendHyperlink(CodeEl, Member);
  2251. if Assigned(TPasProperty(Member).VarType) then
  2252. begin
  2253. AppendSym(CodeEl, ': ');
  2254. AppendHyperlink(CodeEl, TPasProperty(Member).VarType);
  2255. end;
  2256. AppendSym(CodeEl, ';');
  2257. if TPasProperty(Member).IsDefault then
  2258. begin
  2259. AppendKw(CodeEl, ' default');
  2260. AppendSym(CodeEl, ';');
  2261. end;
  2262. SetLength(s, 0);
  2263. if Length(TPasProperty(Member).ReadAccessorName) > 0 then
  2264. s := s + 'r';
  2265. if Length(TPasProperty(Member).WriteAccessorName) > 0 then
  2266. s := s + 'w';
  2267. if Length(TPasProperty(Member).StoredAccessorName) > 0 then
  2268. s := s + 's';
  2269. if Length(s) > 0 then
  2270. AppendText(CodeEl, ' [' + s + ']');
  2271. end else
  2272. AppendText(CreateWarning(CodeEl), '<' + Member.ClassName + '>');
  2273. end;
  2274. CodeEl := CreateCode(CreatePara(CreateTD(CreateTR(TableEl))));
  2275. end;
  2276. AppendText(CodeEl, ' '); // !!!: Dirty trick, necessary for current XML writer
  2277. AppendKw(CodeEl, 'end');
  2278. AppendSym(CodeEl, ';');
  2279. AppendText(CreateH2(BodyElement), SDocInheritance);
  2280. TableEl := CreateTable(BodyElement);
  2281. HaveSeenTObject := AClass.ObjKind <> okClass;
  2282. ThisClass := AClass;
  2283. while True do
  2284. begin
  2285. TREl := CreateTR(TableEl);
  2286. TDEl := CreateTD_vtop(TREl);
  2287. TDEl['align'] := 'center';
  2288. CodeEl := CreateCode(CreatePara(TDEl));
  2289. AppendHyperlink(CodeEl, ThisClass);
  2290. AppendShortDescrCell(TREl, ThisClass);
  2291. if HaveSeenTObject or (CompareText(ThisClass.Name, 'TObject') = 0) then
  2292. HaveSeenTObject := True
  2293. else
  2294. begin
  2295. TDEl := CreateTD(CreateTR(TableEl));
  2296. TDEl['align'] := 'center';
  2297. AppendText(TDEl, '|');
  2298. end;
  2299. if Assigned(ThisClass.AncestorType) then
  2300. begin
  2301. if ThisClass.AncestorType.InheritsFrom(TPasClassType) then
  2302. ThisClass := TPasClassType(ThisClass.AncestorType)
  2303. else
  2304. begin
  2305. TDEl := CreateTD(CreateTR(TableEl));
  2306. TDEl['align'] := 'center';
  2307. AppendText(CreateCode(CreatePara(TDEl)), ThisClass.AncestorType.Name);
  2308. if CompareText(ThisClass.AncestorType.Name, 'TObject') = 0 then
  2309. HaveSeenTObject := True
  2310. else
  2311. begin
  2312. TDEl := CreateTD(CreateTR(TableEl));
  2313. TDEl['align'] := 'center';
  2314. AppendText(TDEl, '?');
  2315. end;
  2316. break;
  2317. end
  2318. end else
  2319. break;
  2320. end;
  2321. if not HaveSeenTObject then
  2322. begin
  2323. TDEl := CreateTD(CreateTR(TableEl));
  2324. TDEl['align'] := 'center';
  2325. AppendText(CreateCode(CreatePara(TDEl)), 'TObject');
  2326. end;
  2327. FinishElementPage(AClass);
  2328. end;
  2329. procedure CreateInheritanceSubpage(AFilter: TMemberFilter);
  2330. var
  2331. ThisClass: TPasClassType;
  2332. i: Integer;
  2333. Member: TPasElement;
  2334. TableEl, TREl, TDEl, ParaEl, LinkEl: TDOMElement;
  2335. begin
  2336. TableEl := CreateTable(BodyElement);
  2337. ThisClass := AClass;
  2338. while True do
  2339. begin
  2340. TREl := CreateTR(TableEl);
  2341. TDEl := CreateTD(TREl);
  2342. TDEl['colspan'] := '3';
  2343. CreateTD(TREl);
  2344. LinkEl := AppendHyperlink(CreateEl(CreateCode(CreatePara(TDEl)), 'b'), ThisClass);
  2345. if Assigned(LinkEl) then
  2346. LinkEl['onClick'] := 'opener.location.href = ''' + LinkEl['href'] +
  2347. '''; return false;';
  2348. for i := 0 to ThisClass.Members.Count - 1 do
  2349. begin
  2350. Member := TPasElement(ThisClass.Members[i]);
  2351. if ((Member.Visibility = visPrivate) and Engine.HidePrivate) or
  2352. ((Member.Visibility = visProtected) and Engine.HideProtected) or
  2353. not AFilter(Member) then
  2354. continue;
  2355. TREl := CreateTR(TableEl);
  2356. ParaEl := CreatePara(CreateTD(TREl));
  2357. case Member.Visibility of
  2358. visPrivate:
  2359. AppendText(ParaEl, 'pv');
  2360. visProtected:
  2361. AppendText(ParaEl, 'pt');
  2362. visPublished:
  2363. AppendText(ParaEl, 'pl');
  2364. end;
  2365. AppendNbSp(ParaEl, 1);
  2366. ParaEl := CreateTD(TREl);
  2367. if (Member.ClassType = TPasProperty) and
  2368. (Length(TPasProperty(Member).WriteAccessorName) = 0) then
  2369. begin
  2370. AppendText(ParaEl, 'ro');
  2371. AppendNbSp(ParaEl, 1);
  2372. end;
  2373. LinkEl := AppendHyperlink(CreatePara(CreateTD(TREl)), Member);
  2374. if Assigned(LinkEl) then
  2375. LinkEl['onClick'] := 'opener.location.href = ''' + LinkEl['href'] +
  2376. '''; return false;';
  2377. end;
  2378. if (not Assigned(ThisClass.AncestorType)) or
  2379. (not (ThisClass.AncestorType.ClassType = TPasClassType)) then
  2380. break;
  2381. ThisClass := TPasClassType(ThisClass.AncestorType);
  2382. AppendNbSp(CreatePara(CreateTD(CreateTR(TableEl))), 1);
  2383. end;
  2384. end;
  2385. procedure CreateSortedSubpage(AFilter: TMemberFilter);
  2386. var
  2387. List: TList;
  2388. ThisClass: TPasClassType;
  2389. i, j: Integer;
  2390. Member: TPasElement;
  2391. TableEl, TREl, TDEl, ParaEl, LinkEl: TDOMElement;
  2392. begin
  2393. List := TList.Create;
  2394. try
  2395. ThisClass := AClass;
  2396. while True do
  2397. begin
  2398. for i := 0 to ThisClass.Members.Count - 1 do
  2399. begin
  2400. Member := TPasElement(ThisClass.Members[i]);
  2401. if (not (((Member.Visibility = visPrivate) and Engine.HidePrivate) or
  2402. ((Member.Visibility = visProtected) and Engine.HideProtected))) and
  2403. AFilter(Member) then
  2404. begin
  2405. j := 0;
  2406. while (j < List.Count) and
  2407. (CompareText(TPasElement(List[j]).Name, Member.Name) < 0) do
  2408. Inc(j);
  2409. List.Insert(j, Member);
  2410. end;
  2411. end;
  2412. if (not Assigned(ThisClass.AncestorType)) or
  2413. (not (ThisClass.AncestorType.ClassType = TPasClassType)) then
  2414. break;
  2415. ThisClass := TPasClassType(ThisClass.AncestorType);
  2416. end;
  2417. TableEl := CreateTable(BodyElement);
  2418. for i := 0 to List.Count - 1 do
  2419. begin
  2420. Member := TPasElement(List[i]);
  2421. TREl := CreateTR(TableEl);
  2422. ParaEl := CreatePara(CreateTD(TREl));
  2423. case Member.Visibility of
  2424. visPrivate:
  2425. AppendText(ParaEl, 'pv');
  2426. visProtected:
  2427. AppendText(ParaEl, 'pt');
  2428. visPublished:
  2429. AppendText(ParaEl, 'pl');
  2430. end;
  2431. AppendNbSp(ParaEl, 1);
  2432. ParaEl := CreatePara(CreateTD(TREl));
  2433. if (Member.ClassType = TPasProperty) and
  2434. (Length(TPasProperty(Member).WriteAccessorName) = 0) then
  2435. begin
  2436. AppendText(ParaEl, 'ro');
  2437. AppendNbSp(ParaEl, 1);
  2438. end;
  2439. TDEl := CreateTD(TREl);
  2440. TDEl['nowrap'] := 'nowrap';
  2441. ParaEl := CreatePara(TDEl);
  2442. LinkEl := AppendHyperlink(ParaEl, Member);
  2443. if Assigned(LinkEl) then
  2444. LinkEl['onClick'] := 'opener.location.href = ''' + LinkEl['href'] +
  2445. '''; return false;';
  2446. AppendText(ParaEl, ' (');
  2447. LinkEl := AppendHyperlink(ParaEl, Member.Parent);
  2448. if Assigned(LinkEl) then
  2449. LinkEl['onClick'] := 'opener.location.href = ''' + LinkEl['href'] +
  2450. '''; return false;';
  2451. AppendText(ParaEl, ')');
  2452. end;
  2453. finally
  2454. List.Free;
  2455. end;
  2456. end;
  2457. begin
  2458. case ASubpageIndex of
  2459. 0:
  2460. CreateMainPage;
  2461. PropertiesByInheritanceSubindex:
  2462. CreateInheritanceSubpage(@PropertyFilter);
  2463. PropertiesByNameSubindex:
  2464. CreateSortedSubpage(@PropertyFilter);
  2465. MethodsByInheritanceSubindex:
  2466. CreateInheritanceSubpage(@MethodFilter);
  2467. MethodsByNameSubindex:
  2468. CreateSortedSubpage(@MethodFilter);
  2469. EventsByInheritanceSubindex:
  2470. CreateInheritanceSubpage(@EventFilter);
  2471. EventsByNameSubindex:
  2472. CreateSortedSubpage(@EventFilter);
  2473. end;
  2474. end;
  2475. procedure THTMLWriter.CreateClassMemberPageBody(AElement: TPasElement);
  2476. var
  2477. TableEl, TREl, CodeEl: TDOMElement;
  2478. procedure CreateVarPage(Element: TPasVariable);
  2479. begin
  2480. AppendHyperlink(CodeEl, Element.Parent);
  2481. AppendSym(CodeEl, '.');
  2482. AppendText(CodeEl, Element.Name);
  2483. if Assigned(Element.VarType) then
  2484. begin
  2485. AppendSym(CodeEl, ': ');
  2486. AppendSym(AppendType(CodeEl, TableEl, Element.VarType, False), ';');
  2487. end;
  2488. end;
  2489. procedure CreatePropertyPage(Element: TPasProperty);
  2490. var
  2491. NeedBreak: Boolean;
  2492. begin
  2493. AppendKw(CodeEl, 'property ');
  2494. AppendHyperlink(CodeEl, Element.Parent);
  2495. AppendSym(CodeEl, '.');
  2496. AppendText(CodeEl, Element.Name);
  2497. if Assigned(Element.VarType) then
  2498. begin
  2499. AppendSym(CodeEl, ': ');
  2500. AppendType(CodeEl, TableEl, Element.VarType, False);
  2501. end;
  2502. NeedBreak := False;
  2503. if Length(TPasProperty(Element).IndexValue) <> 0 then
  2504. begin
  2505. CreateEl(CodeEl, 'br');
  2506. AppendNbsp(CodeEl, 2);
  2507. AppendKw(CodeEl, 'index ');
  2508. AppendPasSHFragment(CodeEl, TPasProperty(Element).IndexValue, 0);
  2509. NeedBreak := True;
  2510. end;
  2511. if Length(TPasProperty(Element).ReadAccessorName) <> 0 then
  2512. begin
  2513. CreateEl(CodeEl, 'br');
  2514. AppendNbsp(CodeEl, 2);
  2515. AppendKw(CodeEl, 'read ');
  2516. AppendText(CodeEl, TPasProperty(Element).ReadAccessorName);
  2517. NeedBreak := True;
  2518. end;
  2519. if Length(TPasProperty(Element).WriteAccessorName) <> 0 then
  2520. begin
  2521. CreateEl(CodeEl, 'br');
  2522. AppendNbsp(CodeEl, 2);
  2523. AppendKw(CodeEl, 'write ');
  2524. AppendText(CodeEl, TPasProperty(Element).WriteAccessorName);
  2525. NeedBreak := True;
  2526. end;
  2527. if Length(TPasProperty(Element).StoredAccessorName) <> 0 then
  2528. begin
  2529. CreateEl(CodeEl, 'br');
  2530. AppendNbsp(CodeEl, 2);
  2531. AppendKw(CodeEl, 'stored ');
  2532. AppendText(CodeEl, TPasProperty(Element).StoredAccessorName);
  2533. NeedBreak := True;
  2534. end;
  2535. if Length(TPasProperty(Element).DefaultValue) <> 0 then
  2536. begin
  2537. CreateEl(CodeEl, 'br');
  2538. AppendNbsp(CodeEl, 2);
  2539. AppendKw(CodeEl, 'default ');
  2540. AppendPasSHFragment(CodeEl, TPasProperty(Element).DefaultValue, 0);
  2541. NeedBreak := True;
  2542. end;
  2543. AppendSym(CodeEl, ';');
  2544. if TPasProperty(Element).IsDefault or TPasProperty(Element).IsNodefault then
  2545. begin
  2546. if NeedBreak then
  2547. begin
  2548. CreateEl(CodeEl, 'br');
  2549. AppendNbsp(CodeEl, 2);
  2550. end;
  2551. if TPasProperty(Element).IsDefault then
  2552. AppendKw(CodeEl, 'default')
  2553. else
  2554. AppendKw(CodeEl, 'nodefault');
  2555. AppendSym(CodeEl, ';');
  2556. end;
  2557. end;
  2558. var
  2559. s: String;
  2560. DocNode: TDocNode;
  2561. begin
  2562. AppendMenuBar(-1);
  2563. AppendTitle(AElement.FullName);
  2564. AppendShortDescr(CreatePara(BodyElement), AElement);
  2565. AppendText(CreateH2(BodyElement), SDocDeclaration);
  2566. AppendSourceRef(AElement);
  2567. TableEl := CreateTable(BodyElement);
  2568. TREl := CreateTR(TableEl);
  2569. CodeEl := CreateCode(CreatePara(CreateTD(TREl)));
  2570. AppendText(CodeEl, ' '); // !!!: Workaround for current HTML writer
  2571. case AElement.Visibility of
  2572. visPrivate: s := 'private';
  2573. visProtected: s := 'protected';
  2574. visPublic: s := 'public';
  2575. visPublished: s := 'published';
  2576. visAutomated: s := 'automated';
  2577. else s := '';
  2578. end;
  2579. if Length(s) > 0 then
  2580. AppendKw(CodeEl, s);
  2581. AppendText(CodeEl, ' ');
  2582. if AElement.ClassType = TPasVariable then
  2583. CreateVarPage(TPasVariable(AElement))
  2584. else if AElement.InheritsFrom(TPasProcedureBase) then
  2585. AppendProcDecl(CodeEl, TableEl, TPasProcedureBase(AElement))
  2586. else if AElement.ClassType = TPasProperty then
  2587. CreatePropertyPage(TPasProperty(AElement))
  2588. else
  2589. AppendText(CreateWarning(BodyElement), '<' + AElement.ClassName + '>');
  2590. FinishElementPage(AElement);
  2591. end;
  2592. procedure THTMLWriter.CreateVarPageBody(AVar: TPasVariable);
  2593. var
  2594. TableEl, TREl, TDEl, CodeEl, El: TDOMElement;
  2595. DocNode: TDocNode;
  2596. begin
  2597. AppendMenuBar(-1);
  2598. AppendTitle(AVar.FullName);
  2599. AppendShortDescr(CreatePara(BodyElement), AVar);
  2600. AppendText(CreateH2(BodyElement), SDocDeclaration);
  2601. AppendSourceRef(AVar);
  2602. TableEl := CreateTable(BodyElement);
  2603. TREl := CreateTR(TableEl);
  2604. TDEl := CreateTD(TREl);
  2605. CodeEl := CreateCode(CreatePara(TDEl));
  2606. AppendKw(CodeEl, 'var');
  2607. AppendText(CodeEl, ' ' + AVar.Name);
  2608. if Assigned(AVar.VarType) then
  2609. begin
  2610. AppendSym(CodeEl, ': ');
  2611. El := AppendType(CodeEl, TableEl, AVar.VarType, False);
  2612. end else
  2613. El := CodeEl;
  2614. if Length(AVar.Value) > 0 then
  2615. AppendPasSHFragment(El, ' = ' + AVar.Value + ';', 0)
  2616. else
  2617. AppendSym(El, ';');
  2618. FinishElementPage(AVar);
  2619. end;
  2620. procedure THTMLWriter.CreateProcPageBody(AProc: TPasProcedureBase);
  2621. var
  2622. TableEl, TREl, TDEl, CodeEl: TDOMElement;
  2623. begin
  2624. AppendMenuBar(-1);
  2625. AppendTitle(AProc.Name);
  2626. AppendShortDescr(CreatePara(BodyElement), AProc);
  2627. AppendText(CreateH2(BodyElement), SDocDeclaration);
  2628. AppendSourceRef(AProc);
  2629. TableEl := CreateTable(BodyElement);
  2630. TREl := CreateTR(TableEl);
  2631. TDEl := CreateTD(TREl);
  2632. CodeEl := CreateCode(CreatePara(TDEl));
  2633. AppendProcDecl(CodeEl, TableEl, AProc);
  2634. FinishElementPage(AProc);
  2635. end;
  2636. Function THTMLWriter.InterPretOption(Const Cmd,Arg : String) : boolean;
  2637. begin
  2638. Result:=True;
  2639. if Cmd = '--html-search' then
  2640. SearchPage := Arg
  2641. else if Cmd = '--footer' then
  2642. FooterFile := Arg
  2643. else
  2644. Result:=False;
  2645. end;
  2646. procedure THTMLWriter.WriteDoc;
  2647. begin
  2648. WriteLn(Format(SWritingPages, [PageCount]));
  2649. WriteHTMLPages;
  2650. end;
  2651. class procedure THTMLWriter.Usage(List: TStrings);
  2652. begin
  2653. List.add('--footer');
  2654. List.Add(SHTMLUsageFooter);
  2655. end;
  2656. // private methods
  2657. function THTMLWriter.GetPageCount: Integer;
  2658. begin
  2659. Result := PageInfos.Count;
  2660. end;
  2661. procedure THTMLWriter.SetOnTest(const AValue: TNotifyEvent);
  2662. begin
  2663. if FOnTest=AValue then exit;
  2664. FOnTest:=AValue;
  2665. end;
  2666. procedure THTMLWriter.CreateAllocator;
  2667. begin
  2668. FAllocator:=TLongNameFileAllocator.Create('.html');
  2669. end;
  2670. procedure THTMWriter.CreateAllocator;
  2671. begin
  2672. FAllocator:=TShortNameFileAllocator.Create('.htm');
  2673. end;
  2674. initialization
  2675. // Do not localize.
  2676. RegisterWriter(THTMLWriter,'html','HTML output using fpdoc.css stylesheet.');
  2677. RegisterWriter(THTMWriter,'htm','HTM (8.3 filenames) output using fpdoc.css stylesheet.');
  2678. finalization
  2679. UnRegisterWriter('html');
  2680. UnRegisterWriter('htm');
  2681. end.