dw_html.pp 87 KB

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