dw_html.pp 107 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632263326342635263626372638263926402641264226432644264526462647264826492650265126522653265426552656265726582659266026612662266326642665266626672668266926702671267226732674267526762677267826792680268126822683268426852686268726882689269026912692269326942695269626972698269927002701270227032704270527062707270827092710271127122713271427152716271727182719272027212722272327242725272627272728272927302731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800280128022803280428052806280728082809281028112812281328142815281628172818281928202821282228232824282528262827282828292830283128322833283428352836283728382839284028412842284328442845284628472848284928502851285228532854285528562857285828592860286128622863286428652866286728682869287028712872287328742875287628772878287928802881288228832884288528862887288828892890289128922893289428952896289728982899290029012902290329042905290629072908290929102911291229132914291529162917291829192920292129222923292429252926292729282929293029312932293329342935293629372938293929402941294229432944294529462947294829492950295129522953295429552956295729582959296029612962296329642965296629672968296929702971297229732974297529762977297829792980298129822983298429852986298729882989299029912992299329942995299629972998299930003001300230033004300530063007300830093010301130123013301430153016301730183019302030213022302330243025302630273028302930303031303230333034303530363037303830393040304130423043304430453046304730483049305030513052305330543055305630573058305930603061306230633064306530663067306830693070307130723073307430753076307730783079308030813082308330843085308630873088308930903091309230933094309530963097309830993100310131023103310431053106310731083109311031113112311331143115311631173118311931203121312231233124312531263127312831293130313131323133313431353136313731383139314031413142314331443145314631473148314931503151315231533154315531563157315831593160316131623163316431653166316731683169317031713172317331743175317631773178317931803181318231833184318531863187318831893190319131923193319431953196319731983199320032013202320332043205320632073208320932103211321232133214321532163217321832193220322132223223322432253226322732283229323032313232323332343235323632373238323932403241324232433244324532463247324832493250325132523253325432553256325732583259326032613262326332643265326632673268326932703271327232733274327532763277327832793280328132823283328432853286328732883289329032913292329332943295329632973298329933003301330233033304330533063307330833093310331133123313331433153316331733183319332033213322332333243325332633273328332933303331333233333334333533363337333833393340334133423343334433453346334733483349335033513352335333543355335633573358335933603361336233633364336533663367336833693370337133723373337433753376337733783379338033813382338333843385338633873388338933903391339233933394339533963397339833993400340134023403340434053406340734083409341034113412341334143415341634173418341934203421342234233424342534263427342834293430343134323433343434353436343734383439344034413442344334443445344634473448344934503451345234533454345534563457345834593460346134623463346434653466346734683469347034713472347334743475347634773478347934803481348234833484348534863487348834893490349134923493349434953496349734983499350035013502350335043505350635073508350935103511351235133514351535163517351835193520352135223523352435253526352735283529353035313532353335343535353635373538353935403541354235433544354535463547354835493550355135523553355435553556355735583559356035613562356335643565356635673568356935703571357235733574357535763577357835793580358135823583358435853586358735883589359035913592359335943595359635973598359936003601360236033604360536063607360836093610361136123613361436153616361736183619362036213622362336243625362636273628362936303631363236333634363536363637363836393640364136423643364436453646364736483649365036513652365336543655365636573658365936603661366236633664366536663667366836693670367136723673367436753676367736783679368036813682368336843685368636873688368936903691369236933694369536963697369836993700370137023703370437053706370737083709371037113712371337143715371637173718371937203721372237233724372537263727372837293730373137323733373437353736373737383739374037413742374337443745374637473748374937503751375237533754375537563757375837593760376137623763376437653766376737683769377037713772377337743775377637773778377937803781378237833784378537863787378837893790379137923793379437953796379737983799380038013802380338043805380638073808380938103811381238133814381538163817381838193820382138223823382438253826382738283829383038313832383338343835383638373838383938403841384238433844384538463847384838493850385138523853
  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, contnrs, 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. IndexSubIndex = 8;
  28. ClassHierarchySubIndex = 9;
  29. // Subpage indices for classes
  30. PropertiesByInheritanceSubindex = 1;
  31. PropertiesByNameSubindex = 2;
  32. MethodsByInheritanceSubindex = 3;
  33. MethodsByNameSubindex = 4;
  34. EventsByInheritanceSubindex = 5;
  35. EventsByNameSubindex = 6;
  36. type
  37. TFileAllocator = class
  38. public
  39. procedure AllocFilename(AElement: TPasElement; ASubindex: Integer); virtual;
  40. function GetFilename(AElement: TPasElement;
  41. ASubindex: Integer): String; virtual; abstract;
  42. function GetRelativePathToTop(AElement: TPasElement): String; virtual;
  43. function GetCSSFilename(ARelativeTo: TPasElement): DOMString; virtual;
  44. end;
  45. TShortNameFileAllocator = class(TFileAllocator)
  46. private
  47. FExtension: String;
  48. public
  49. constructor Create(const AExtension: String);
  50. procedure AllocFilename(AElement: TPasElement; ASubindex: Integer); override;
  51. property Extension: String read FExtension;
  52. end;
  53. TLongNameFileAllocator = class(TFileAllocator)
  54. private
  55. FExtension: String;
  56. public
  57. constructor Create(const AExtension: String);
  58. function GetFilename(AElement: TPasElement;
  59. ASubindex: Integer): String; override;
  60. function GetRelativePathToTop(AElement: TPasElement): String; override;
  61. property Extension: String read FExtension;
  62. end;
  63. TPageInfo = class
  64. Element: TPasElement;
  65. SubpageIndex: Integer;
  66. end;
  67. { THTMLWriter }
  68. THTMLWriter = class(TFPDocWriter)
  69. private
  70. FImageFileList: TStrings;
  71. FOnTest: TNotifyEvent;
  72. FPackage: TPasPackage;
  73. FCharSet : String;
  74. procedure AddElementsFromList(L: TStrings; List: TFPList; UsePathName : Boolean = False);
  75. procedure AppendTypeDecl(AType: TPasType; TableEl, CodeEl: TDomElement);
  76. procedure CreateMinusImage;
  77. procedure CreatePlusImage;
  78. function GetPageCount: Integer;
  79. procedure SetOnTest(const AValue: TNotifyEvent);
  80. protected
  81. FCSSFile: String;
  82. FAllocator: TFileAllocator;
  83. CurDirectory: String; // relative to curdir of process
  84. BaseDirectory: String; // relative path to package base directory
  85. PageInfos: TObjectList; // list of TPageInfo objects
  86. Doc: THTMLDocument;
  87. HeadElement,
  88. BodyElement, TitleElement: TDOMElement;
  89. Module: TPasModule;
  90. OutputNodeStack: TList;
  91. CurOutputNode: TDOMNode;
  92. InsideHeadRow, DoPasHighlighting: Boolean;
  93. HighlighterFlags: Byte;
  94. FooterFile: string;
  95. FIDF : Boolean;
  96. FDateFormat: String;
  97. FIndexColCount : Integer;
  98. FSearchPage : String;
  99. FBaseImageURL : String;
  100. FUseMenuBrackets: Boolean;
  101. Procedure CreateAllocator; virtual;
  102. procedure CreateCSSFile; virtual;
  103. function ResolveLinkID(const Name: String; Level : Integer = 0): DOMString;
  104. function ResolveLinkIDInUnit(const Name,AUnitName: String): DOMString;
  105. function ResolveLinkWithinPackage(AElement: TPasElement;
  106. ASubpageIndex: Integer): String;
  107. // Helper functions for creating DOM elements
  108. function CreateEl(Parent: TDOMNode; const AName: DOMString): THTMLElement;
  109. function CreatePara(Parent: TDOMNode): THTMLElement;
  110. function CreateH1(Parent: TDOMNode): THTMLElement;
  111. function CreateH2(Parent: TDOMNode): THTMLElement;
  112. function CreateH3(Parent: TDOMNode): THTMLElement;
  113. function CreateTable(Parent: TDOMNode; const AClass: DOMString = ''): THTMLElement;
  114. function CreateContentTable(Parent: TDOMNode): THTMLElement;
  115. function CreateTR(Parent: TDOMNode): THTMLElement;
  116. function CreateTD(Parent: TDOMNode): THTMLElement;
  117. function CreateTD_vtop(Parent: TDOMNode): THTMLElement;
  118. function CreateLink(Parent: TDOMNode; const AHRef: DOMString): THTMLElement;
  119. function CreateAnchor(Parent: TDOMNode; const AName: DOMString): THTMLElement;
  120. function CreateCode(Parent: TDOMNode): THTMLElement;
  121. function CreateWarning(Parent: TDOMNode): THTMLElement;
  122. // Description node conversion
  123. Procedure DescrEmitNotesHeader(AContext : TPasElement); override;
  124. Procedure DescrEmitNotesFooter(AContext : TPasElement); override;
  125. procedure PushOutputNode(ANode: TDOMNode);
  126. procedure PopOutputNode;
  127. procedure DescrWriteText(const AText: DOMString); override;
  128. procedure DescrBeginBold; override;
  129. procedure DescrEndBold; override;
  130. procedure DescrBeginItalic; override;
  131. procedure DescrEndItalic; override;
  132. procedure DescrBeginEmph; override;
  133. procedure DescrEndEmph; override;
  134. procedure DescrWriteImageEl(const AFileName, ACaption, ALinkName : DOMString); override;
  135. procedure DescrWriteFileEl(const AText: DOMString); override;
  136. procedure DescrWriteKeywordEl(const AText: DOMString); override;
  137. procedure DescrWriteVarEl(const AText: DOMString); override;
  138. procedure DescrBeginLink(const AId: DOMString); override;
  139. procedure DescrEndLink; override;
  140. procedure DescrBeginURL(const AURL: DOMString); override;
  141. procedure DescrEndURL; override;
  142. procedure DescrWriteLinebreak; override;
  143. procedure DescrBeginParagraph; override;
  144. procedure DescrEndParagraph; override;
  145. procedure DescrBeginCode(HasBorder: Boolean; const AHighlighterName: String); override;
  146. procedure DescrWriteCodeLine(const ALine: String); override;
  147. procedure DescrEndCode; override;
  148. procedure DescrBeginOrderedList; override;
  149. procedure DescrEndOrderedList; override;
  150. procedure DescrBeginUnorderedList; override;
  151. procedure DescrEndUnorderedList; override;
  152. procedure DescrBeginDefinitionList; override;
  153. procedure DescrEndDefinitionList; override;
  154. procedure DescrBeginListItem; override;
  155. procedure DescrEndListItem; override;
  156. procedure DescrBeginDefinitionTerm; override;
  157. procedure DescrEndDefinitionTerm; override;
  158. procedure DescrBeginDefinitionEntry; override;
  159. procedure DescrEndDefinitionEntry; override;
  160. procedure DescrBeginSectionTitle; override;
  161. procedure DescrBeginSectionBody; override;
  162. procedure DescrEndSection; override;
  163. procedure DescrBeginRemark; override;
  164. procedure DescrEndRemark; override;
  165. procedure DescrBeginTable(ColCount: Integer; HasBorder: Boolean); override;
  166. procedure DescrEndTable; override;
  167. procedure DescrBeginTableCaption; override;
  168. procedure DescrEndTableCaption; override;
  169. procedure DescrBeginTableHeadRow; override;
  170. procedure DescrEndTableHeadRow; override;
  171. procedure DescrBeginTableRow; override;
  172. procedure DescrEndTableRow; override;
  173. procedure DescrBeginTableCell; override;
  174. procedure DescrEndTableCell; override;
  175. procedure AppendText(Parent: TDOMNode; const AText: DOMString);
  176. procedure AppendNbSp(Parent: TDOMNode; ACount: Integer);
  177. procedure AppendSym(Parent: TDOMNode; const AText: DOMString);
  178. procedure AppendKw(Parent: TDOMNode; const AText: DOMString);
  179. function AppendPasSHFragment(Parent: TDOMNode; const AText: String;
  180. AShFlags: Byte): Byte;
  181. Procedure AppendShortDescr(AContext : TPasElement;Parent: TDOMNode; DocNode : TDocNode);
  182. procedure AppendShortDescr(Parent: TDOMNode; Element: TPasElement);
  183. procedure AppendShortDescrCell(Parent: TDOMNode; Element: TPasElement);
  184. procedure AppendDescr(AContext: TPasElement; Parent: TDOMNode;
  185. DescrNode: TDOMElement; AutoInsertBlock: Boolean);
  186. procedure AppendDescrSection(AContext: TPasElement; Parent: TDOMNode;
  187. DescrNode: TDOMElement; const ATitle: DOMString);
  188. function AppendHyperlink(Parent: TDOMNode; Element: TPasElement): TDOMElement;
  189. function AppendType(CodeEl, TableEl: TDOMElement;
  190. Element: TPasType; Expanded: Boolean;
  191. NestingLevel: Integer = 0): TDOMElement;
  192. function AppendProcType(CodeEl, TableEl: TDOMElement;
  193. Element: TPasProcedureType; Indent: Integer): TDOMElement;
  194. procedure AppendProcExt(CodeEl: TDOMElement; Element: TPasProcedure);
  195. procedure AppendProcDecl(CodeEl, TableEl: TDOMElement;
  196. Element: TPasProcedureBase);
  197. procedure AppendProcArgsSection(Parent: TDOMNode;
  198. Element: TPasProcedureType; SkipResult : Boolean = False);
  199. function AppendRecordType(CodeEl, TableEl: TDOMElement;
  200. Element: TPasRecordType; NestingLevel: Integer): TDOMElement;
  201. procedure AppendTitle(const AText: DOMString);
  202. procedure AppendMenuBar(ASubpageIndex: Integer);
  203. procedure AppendTopicMenuBar(Topic : TTopicElement);
  204. procedure AppendSourceRef(AElement: TPasElement);
  205. procedure FinishElementPage(AElement: TPasElement);
  206. Procedure AppendSeeAlsoSection(AElement : TPasElement;DocNode : TDocNode);
  207. Procedure AppendExampleSection(AElement : TPasElement;DocNode : TDocNode);
  208. procedure AppendFooter;
  209. procedure CreateIndexPage(L : TStringList);
  210. procedure CreateModuleIndexPage(AModule: TPasModule);
  211. procedure CreatePageBody(AElement: TPasElement; ASubpageIndex: Integer); virtual;
  212. procedure CreatePackagePageBody;
  213. procedure CreatePackageIndex;
  214. procedure CreatePackageClassHierarchy;
  215. procedure CreateClassHierarchyPage(AList: TStringList; AddUnit : Boolean);
  216. procedure AddModuleIdentifiers(AModule : TPasModule; L : TStrings);
  217. Procedure CreateTopicPageBody(AElement : TTopicElement);
  218. procedure CreateModulePageBody(AModule: TPasModule; ASubpageIndex: Integer);
  219. procedure CreateConstPageBody(AConst: TPasConst);
  220. procedure CreateTypePageBody(AType: TPasType);
  221. procedure CreateClassPageBody(AClass: TPasClassType; ASubpageIndex: Integer);
  222. procedure CreateClassMemberPageBody(AElement: TPasElement);
  223. procedure CreateVarPageBody(AVar: TPasVariable);
  224. procedure CreateProcPageBody(AProc: TPasProcedureBase);
  225. Procedure CreateTopicLinks(Node : TDocNode; PasElement : TPasElement);
  226. public
  227. constructor Create(APackage: TPasPackage; AEngine: TFPDocEngine); override;
  228. destructor Destroy; override;
  229. // Single-page generation
  230. function CreateHTMLPage(AElement: TPasElement;
  231. ASubpageIndex: Integer): TXMLDocument;
  232. function CreateXHTMLPage(AElement: TPasElement;
  233. ASubpageIndex: Integer): TXMLDocument;
  234. // For producing complete package documentation
  235. procedure WriteHTMLPages; virtual;
  236. procedure WriteXHTMLPages;
  237. Function InterPretOption(Const Cmd,Arg : String) : boolean; override;
  238. Procedure WriteDoc; override;
  239. Class Function FileNameExtension : String; override;
  240. class procedure Usage(List: TStrings); override;
  241. Class procedure SplitImport(var AFilename, ALinkPrefix: String); override;
  242. Property SearchPage: String Read FSearchPage Write FSearchPage;
  243. property Allocator: TFileAllocator read FAllocator;
  244. property Package: TPasPackage read FPackage;
  245. property PageCount: Integer read GetPageCount;
  246. Property IncludeDateInFooter : Boolean Read FIDF Write FIDF;
  247. Property DateFormat : String Read FDateFormat Write FDateFormat;
  248. property OnTest: TNotifyEvent read FOnTest write SetOnTest;
  249. Property CharSet : String Read FCharSet Write FCharSet;
  250. Property IndexColCount : Integer Read FIndexColCount write FIndexColCount;
  251. Property BaseImageURL : String Read FBaseImageURL Write FBaseImageURL;
  252. Property UseMenuBrackets : Boolean Read FUseMenuBrackets write FUseMenuBrackets;
  253. end;
  254. THTMWriter = class(THTMLWriter)
  255. Protected
  256. Procedure CreateAllocator; override;
  257. end;
  258. {$DEFINE chmInterface}
  259. {$I dw_htmlchm.inc}
  260. {$UNDEF chmInterface}
  261. implementation
  262. uses SysUtils, XHTML, XMLRead, XMLWrite, HTMWrite, sh_pas, fpdocclasstree,
  263. chmsitemap;
  264. {$i css.inc}
  265. {$i plusimage.inc}
  266. {$i minusimage.inc}
  267. Function FixHTMLpath(S : String) : STring;
  268. begin
  269. Result:=StringReplace(S,'\','/',[rfReplaceAll]);
  270. end;
  271. {$I dw_htmlchm.inc}
  272. procedure TFileAllocator.AllocFilename(AElement: TPasElement;
  273. ASubindex: Integer);
  274. begin
  275. end;
  276. function TFileAllocator.GetRelativePathToTop(AElement: TPasElement): String;
  277. begin
  278. SetLength(Result, 0);
  279. end;
  280. function TFileAllocator.GetCSSFilename(ARelativeTo: TPasElement): DOMString;
  281. begin
  282. Result := GetRelativePathToTop(ARelativeTo) + 'fpdoc.css';
  283. end;
  284. constructor TShortNameFileAllocator.Create(const AExtension: String);
  285. begin
  286. inherited Create;
  287. FExtension := AExtension;
  288. end;
  289. procedure TShortNameFileAllocator.AllocFilename(AElement: TPasElement;
  290. ASubindex: Integer);
  291. begin
  292. // !!!: Add element to file list
  293. end;
  294. constructor TLongNameFileAllocator.Create(const AExtension: String);
  295. begin
  296. inherited Create;
  297. FExtension := AExtension;
  298. end;
  299. function TLongNameFileAllocator.GetFilename(AElement: TPasElement;
  300. ASubindex: Integer): String;
  301. var
  302. s: String;
  303. i: Integer;
  304. begin
  305. if AElement.ClassType = TPasPackage then
  306. Result := 'index'
  307. else if AElement.ClassType = TPasModule then
  308. Result := LowerCase(AElement.Name) + PathDelim + 'index'
  309. else
  310. begin
  311. if AElement is TPasOperator then
  312. begin
  313. Result := LowerCase(AElement.Parent.PathName) + '.op-';
  314. s := Copy(AElement.Name, Pos(' ', AElement.Name) + 1, Length(AElement.Name));
  315. s := Copy(s, 1, Pos('(', s) - 1);
  316. if s = ':=' then
  317. s := 'assign'
  318. else if s = '+' then
  319. s := 'add'
  320. else if s = '-' then
  321. s := 'sub'
  322. else if s = '*' then
  323. s := 'mul'
  324. else if s = '/' then
  325. s := 'div'
  326. else if s = '**' then
  327. s := 'power'
  328. else if s = '=' then
  329. s := 'equal'
  330. else if s = '<>' then
  331. s := 'unequal'
  332. else if s = '<' then
  333. s := 'less'
  334. else if s = '<=' then
  335. s := 'lessequal'
  336. else if s = '>' then
  337. s := 'greater'
  338. else if s = '>=' then
  339. s := 'greaterthan'
  340. else if s = '><' then
  341. s := 'symmetricdifference';
  342. Result := Result + s + '-';
  343. s := '';
  344. i := 1;
  345. while AElement.Name[i] <> '(' do
  346. Inc(i);
  347. Inc(i);
  348. while AElement.Name[i] <> ')' do
  349. begin
  350. if AElement.Name[i] = ',' then
  351. begin
  352. s := s + '-';
  353. Inc(i);
  354. end else
  355. s := s + AElement.Name[i];
  356. Inc(i);
  357. end;
  358. Result := Result + LowerCase(s) + '-' + LowerCase(Copy(AElement.Name,
  359. Pos('):', AElement.Name) + 3, Length(AElement.Name)));
  360. end else
  361. Result := LowerCase(AElement.PathName);
  362. // searching for TPasModule - it is on the 2nd level
  363. if Assigned(AElement.Parent) then
  364. while Assigned(AElement.Parent.Parent) do
  365. AElement := AElement.Parent;
  366. // cut off Package Name
  367. Result := Copy(Result, Length(AElement.Parent.Name) + 2, MaxInt);
  368. // to skip dots in unit name
  369. i := Length(AElement.Name);
  370. while (i <= Length(Result)) and (Result[i] <> '.') do
  371. Inc(i);
  372. if (i <= Length(Result)) and (i > 0) then
  373. Result[i] := PathDelim;
  374. end;
  375. if ASubindex > 0 then
  376. Result := Result + '-' + IntToStr(ASubindex);
  377. Result := Result + Extension;
  378. end;
  379. function TLongNameFileAllocator.GetRelativePathToTop(AElement: TPasElement): String;
  380. begin
  381. if (AElement.ClassType=TPasPackage) then
  382. Result := ''
  383. else if (AElement.ClassType=TTopicElement) then
  384. begin
  385. If (AElement.Parent.ClassType=TTopicElement) then
  386. Result:='../'+GetRelativePathToTop(AElement.Parent)
  387. else if (AElement.Parent.ClassType=TPasPackage) then
  388. Result:=''
  389. else if (AElement.Parent.ClassType=TPasModule) then
  390. Result:='../';
  391. end
  392. else
  393. Result := '../';
  394. end;
  395. Type
  396. { TLinkData }
  397. TLinkData = Class(TObject)
  398. FPathName,
  399. FLink,
  400. FModuleName : String;
  401. Constructor Create(Const APathName,ALink,AModuleName : string);
  402. end;
  403. { TLinkData }
  404. constructor TLinkData.Create(Const APathName, ALink, AModuleName: string);
  405. begin
  406. FPathName:=APathName;
  407. FLink:=ALink;
  408. FModuleName:=AModuleName;
  409. end;
  410. constructor THTMLWriter.Create(APackage: TPasPackage; AEngine: TFPDocEngine);
  411. procedure AddPage(AElement: TPasElement; ASubpageIndex: Integer);
  412. var
  413. PageInfo: TPageInfo;
  414. begin
  415. PageInfo := TPageInfo.Create;
  416. PageInfo.Element := AElement;
  417. PageInfo.SubpageIndex := ASubpageIndex;
  418. PageInfos.Add(PageInfo);
  419. Allocator.AllocFilename(AElement, ASubpageIndex);
  420. if ASubpageIndex = 0 then
  421. Engine.AddLink(AElement.PathName,
  422. Allocator.GetFilename(AElement, ASubpageIndex));
  423. end;
  424. procedure AddTopicPages(AElement: TPasElement);
  425. var
  426. PreviousTopic,
  427. TopicElement : TTopicElement;
  428. PageInfo : TPageInfo;
  429. DocNode,
  430. TopicNode : TDocNode;
  431. begin
  432. DocNode:=Engine.FindDocNode(AElement);
  433. If not Assigned(DocNode) then
  434. exit;
  435. TopicNode:=DocNode.FirstChild;
  436. PreviousTopic:=Nil;
  437. While Assigned(TopicNode) do
  438. begin
  439. If TopicNode.TopicNode then
  440. begin
  441. TopicElement:=TTopicElement.Create(TopicNode.Name,AElement);
  442. Topics.Add(TopicElement);
  443. TopicElement.TopicNode:=TopicNode;
  444. TopicElement.Previous:=PreviousTopic;
  445. If Assigned(PreviousTopic) then
  446. PreviousTopic.Next:=TopicElement;
  447. PreviousTopic:=TopicElement;
  448. if AElement is TTopicElement then
  449. TTopicElement(AElement).SubTopics.Add(TopicElement);
  450. PageInfo := TPageInfo.Create;
  451. PageInfo.Element := TopicElement;
  452. PageInfo.SubpageIndex := 0;
  453. PageInfos.Add(PageInfo);
  454. Allocator.AllocFilename(TopicElement,0);
  455. Engine.AddLink(TopicElement.PathName, Allocator.GetFilename(TopicElement,0));
  456. if AElement is TTopicElement then
  457. TTopicElement(AElement).SubTopics.Add(TopicElement)
  458. else // Only one level of recursion.
  459. AddTopicPages(TopicElement);
  460. end;
  461. TopicNode:=TopicNode.NextSibling;
  462. end;
  463. end;
  464. procedure AddPages(AElement: TPasElement; ASubpageIndex: Integer;
  465. AList: TFPList);
  466. var
  467. i: Integer;
  468. begin
  469. if AList.Count > 0 then
  470. begin
  471. AddPage(AElement, ASubpageIndex);
  472. for i := 0 to AList.Count - 1 do
  473. AddPage(TPasElement(AList[i]), 0);
  474. end;
  475. end;
  476. Function HaveClasses(AModule: TPasModule) : Boolean;
  477. begin
  478. with AModule do
  479. Result:=InterfaceSection.Classes.Count>0;
  480. end;
  481. procedure ScanModule(AModule: TPasModule; LinkList : TObjectList);
  482. var
  483. i, j, k: Integer;
  484. s: String;
  485. ClassEl: TPasClassType;
  486. FPEl, AncestorMemberEl: TPasElement;
  487. DocNode: TDocNode;
  488. ALink : DOMString;
  489. DidAutolink: Boolean;
  490. begin
  491. AddPage(AModule, 0);
  492. AddPage(AModule,IndexSubIndex);
  493. AddTopicPages(AModule);
  494. with AModule do
  495. begin
  496. if InterfaceSection.ResStrings.Count > 0 then
  497. begin
  498. AddPage(AModule, ResstrSubindex);
  499. s := Allocator.GetFilename(AModule, ResstrSubindex);
  500. for i := 0 to InterfaceSection.ResStrings.Count - 1 do
  501. with TPasResString(InterfaceSection.ResStrings[i]) do
  502. Engine.AddLink(PathName, s + '#' + LowerCase(Name));
  503. end;
  504. AddPages(AModule, ConstsSubindex, InterfaceSection.Consts);
  505. AddPages(AModule, TypesSubindex, InterfaceSection.Types);
  506. if InterfaceSection.Classes.Count > 0 then
  507. begin
  508. AddPage(AModule, ClassesSubindex);
  509. for i := 0 to InterfaceSection.Classes.Count - 1 do
  510. begin
  511. ClassEl := TPasClassType(InterfaceSection.Classes[i]);
  512. AddPage(ClassEl, 0);
  513. // !!!: Only add when there are items
  514. AddPage(ClassEl, PropertiesByInheritanceSubindex);
  515. AddPage(ClassEl, PropertiesByNameSubindex);
  516. AddPage(ClassEl, MethodsByInheritanceSubindex);
  517. AddPage(ClassEl, MethodsByNameSubindex);
  518. AddPage(ClassEl, EventsByInheritanceSubindex);
  519. AddPage(ClassEl, EventsByNameSubindex);
  520. for j := 0 to ClassEl.Members.Count - 1 do
  521. begin
  522. FPEl := TPasElement(ClassEl.Members[j]);
  523. if ((FPEl.Visibility = visPrivate) and Engine.HidePrivate) or
  524. ((FPEl.Visibility = visProtected) and Engine.HideProtected) then
  525. continue;
  526. DocNode := Engine.FindDocNode(FPEl);
  527. if Assigned(DocNode) then
  528. begin
  529. if Assigned(DocNode.Node) then
  530. ALink:=DocNode.Node['link']
  531. else
  532. ALink:='';
  533. If (ALink<>'') then
  534. LinkList.Add(TLinkData.Create(FPEl.PathName,ALink,AModule.name))
  535. else
  536. AddPage(FPEl, 0);
  537. end
  538. else
  539. begin
  540. DidAutolink := False;
  541. if Assigned(ClassEl.AncestorType) and
  542. (ClassEl.AncestorType.ClassType = TPasClassType) then
  543. begin
  544. for k := 0 to TPasClassType(ClassEl.AncestorType).Members.Count - 1 do
  545. begin
  546. AncestorMemberEl :=
  547. TPasElement(TPasClassType(ClassEl.AncestorType).Members[k]);
  548. if AncestorMemberEl.Name = FPEl.Name then
  549. begin
  550. DocNode := Engine.FindDocNode(AncestorMemberEl);
  551. if Assigned(DocNode) then
  552. begin
  553. DidAutolink := True;
  554. Engine.AddLink(FPEl.PathName,
  555. Engine.FindAbsoluteLink(AncestorMemberEl.PathName));
  556. break;
  557. end;
  558. end;
  559. end;
  560. end;
  561. if not DidAutolink then
  562. AddPage(FPEl, 0);
  563. end;
  564. end;
  565. end;
  566. end;
  567. AddPages(AModule, ProcsSubindex, InterfaceSection.Functions);
  568. AddPages(AModule, VarsSubindex, InterfaceSection.Variables);
  569. end;
  570. end;
  571. var
  572. i: Integer;
  573. L : TObjectList;
  574. H : Boolean;
  575. begin
  576. inherited ;
  577. // should default to true since this is the old behavior
  578. UseMenuBrackets:=True;
  579. IndexColCount:=3;
  580. Charset:='iso-8859-1';
  581. CreateAllocator;
  582. FPackage := APackage;
  583. OutputNodeStack := TList.Create;
  584. PageInfos := TObjectList.Create;
  585. FImageFileList := TStringList.Create;
  586. // Allocate page for the package itself, if a name is given (i.e. <> '#')
  587. if Length(Package.Name) > 1 then
  588. begin
  589. AddPage(Package, 0);
  590. AddPage(Package,IndexSubIndex);
  591. I:=0;
  592. H:=False;
  593. While (I<Package.Modules.Count) and Not H do
  594. begin
  595. H:=HaveClasses(TPasModule(Package.Modules[i]));
  596. Inc(I);
  597. end;
  598. if H then
  599. AddPage(Package,ClassHierarchySubIndex);
  600. AddTopicPages(Package);
  601. end;
  602. L:=TObjectList.Create;
  603. try
  604. for i := 0 to Package.Modules.Count - 1 do
  605. ScanModule(TPasModule(Package.Modules[i]),L);
  606. // Resolve links
  607. For I:=0 to L.Count-1 do
  608. With TLinkData(L[i]) do
  609. Engine.AddLink(FPathName,ResolveLinkIDInUnit(FLink,FModuleName));
  610. finally
  611. L.Free;
  612. end;
  613. end;
  614. destructor THTMLWriter.Destroy;
  615. begin
  616. PageInfos.Free;
  617. OutputNodeStack.Free;
  618. FAllocator.Free;
  619. FImageFileList.Free;
  620. inherited Destroy;
  621. end;
  622. function THTMLWriter.CreateHTMLPage(AElement: TPasElement;
  623. ASubpageIndex: Integer): TXMLDocument;
  624. var
  625. HTMLEl: THTMLHtmlElement;
  626. HeadEl: THTMLHeadElement;
  627. El: TDOMElement;
  628. begin
  629. Doc := THTMLDocument.Create;
  630. Result := Doc;
  631. Doc.AppendChild(Doc.Impl.CreateDocumentType(
  632. 'HTML', '-//W3C//DTD HTML 4.01 Transitional//EN',
  633. 'http://www.w3.org/TR/html4/loose.dtd'));
  634. HTMLEl := Doc.CreateHtmlElement;
  635. Doc.AppendChild(HTMLEl);
  636. HeadEl := Doc.CreateHeadElement;
  637. HeadElement:=HeadEl;
  638. HTMLEl.AppendChild(HeadEl);
  639. El := Doc.CreateElement('meta');
  640. HeadEl.AppendChild(El);
  641. El['http-equiv'] := 'Content-Type';
  642. El['content'] := 'text/html; charset=utf-8';
  643. TitleElement := Doc.CreateElement('title');
  644. HeadEl.AppendChild(TitleElement);
  645. El := Doc.CreateElement('link');
  646. BodyElement := Doc.CreateElement('body');
  647. HTMLEl.AppendChild(BodyElement);
  648. CreatePageBody(AElement, ASubpageIndex);
  649. AppendFooter;
  650. HeadEl.AppendChild(El);
  651. El['rel'] := 'stylesheet';
  652. El['type'] := 'text/css';
  653. El['href'] := FixHtmlPath(Allocator.GetCSSFilename(AElement));
  654. end;
  655. function THTMLWriter.CreateXHTMLPage(AElement: TPasElement;
  656. ASubpageIndex: Integer): TXMLDocument;
  657. begin
  658. Result := nil;
  659. end;
  660. procedure CreatePath(const AFilename: String);
  661. var
  662. EndIndex: Integer;
  663. Path: String;
  664. begin
  665. EndIndex := Length(AFilename);
  666. if EndIndex = 0 then
  667. exit;
  668. while not (AFilename[EndIndex] in AllowDirectorySeparators) do
  669. begin
  670. Dec(EndIndex);
  671. if EndIndex = 0 then
  672. exit;
  673. end;
  674. Path := Copy(AFilename, 1, EndIndex - 1);
  675. if not DirectoryExists(Path) then
  676. begin
  677. CreatePath(Path);
  678. MkDir(Path);
  679. end;
  680. end;
  681. procedure THTMLWriter.WriteHTMLPages;
  682. var
  683. i: Integer;
  684. PageDoc: TXMLDocument;
  685. Filename: String;
  686. begin
  687. if Engine.Output <> '' then
  688. Engine.Output := IncludeTrailingBackSlash(Engine.Output);
  689. for i := 0 to PageInfos.Count - 1 do
  690. with TPageInfo(PageInfos[i]) do
  691. begin
  692. PageDoc := CreateHTMLPage(Element, SubpageIndex);
  693. try
  694. Filename := Engine.Output + Allocator.GetFilename(Element, SubpageIndex);
  695. try
  696. CreatePath(Filename);
  697. WriteHTMLFile(PageDoc, Filename);
  698. except
  699. on E: Exception do
  700. DoLog(SErrCouldNotCreateFile, [FileName, e.Message]);
  701. end;
  702. finally
  703. PageDoc.Free;
  704. end;
  705. end;
  706. CreateCSSFile;
  707. CreatePlusImage;
  708. CreateMinusImage;
  709. end;
  710. procedure THTMLWriter.CreatePlusImage;
  711. Var
  712. TempStream: TMemoryStream;
  713. begin
  714. TempStream := TMemoryStream.Create;
  715. try
  716. DoLog('Creating plus image',[]);
  717. TempStream.WriteBuffer(PlusImageData,SizeOf(PlusImageData));
  718. TempStream.Position := 0;
  719. TempStream.SaveToFile(Engine.output+'plus.png');
  720. finally
  721. TempStream.Free;
  722. end;
  723. end;
  724. procedure THTMLWriter.CreateMinusImage;
  725. Var
  726. TempStream: TMemoryStream;
  727. begin
  728. TempStream := TMemoryStream.Create;
  729. try
  730. DoLog('Creating minus image',[]);
  731. TempStream.WriteBuffer(MinusImageData,SizeOf(MinusImageData));
  732. TempStream.Position := 0;
  733. TempStream.SaveToFile(Engine.output+'minus.png');
  734. finally
  735. TempStream.Free;
  736. end;
  737. end;
  738. procedure THTMLWriter.CreateCSSFile;
  739. Var
  740. TempStream: TMemoryStream;
  741. begin
  742. TempStream := TMemoryStream.Create;
  743. try
  744. if (FCSSFile<>'') then
  745. begin
  746. if not FileExists(FCSSFile) then
  747. begin
  748. DoLog('Can''t find CSS file "%s"',[FCSSFILE]);
  749. halt(1);
  750. end;
  751. TempStream.LoadFromFile(FCSSFile);
  752. end
  753. else
  754. begin
  755. DoLog('Using built-in CSS file',[]);
  756. TempStream.WriteBuffer(DefaultCSS,SizeOf(DefaultCSS));
  757. end;
  758. TempStream.Position := 0;
  759. TempStream.SaveToFile(Engine.output+'fpdoc.css');
  760. finally
  761. TempStream.Free;
  762. end;
  763. end;
  764. procedure THTMLWriter.WriteXHTMLPages;
  765. begin
  766. end;
  767. {procedure THTMLWriter.CreateDoc(const ATitle: DOMString;
  768. AElement: TPasElement; const AFilename: String);
  769. var
  770. El: TDOMElement;
  771. DocInfo: TDocInfo;
  772. CSSName: String;
  773. begin
  774. Doc := TXHTMLDocument.Create;
  775. with TXHTMLDocument(Doc) do
  776. begin
  777. Encoding := 'ISO8859-1';
  778. CSSName := 'fpdoc.css';
  779. if Assigned(Module) then
  780. CSSName := '../' + CSSName;
  781. $IFNDEF ver1_0
  782. StylesheetType := 'text/css';
  783. StylesheetHRef := CSSName;
  784. $ENDIF
  785. CreateRoot(xhtmlStrict);
  786. with RequestHeadElement do
  787. begin
  788. AppendText(RequestTitleElement, ATitle);
  789. El := CreateElement('link');
  790. AppendChild(El);
  791. El['rel'] := 'stylesheet';
  792. El['type'] := 'text/css';
  793. El['href'] := FixHtmlPath(CSSName);
  794. end;
  795. Self.BodyElement := RequestBodyElement('en');
  796. end;
  797. if Length(AFilename) > 0 then
  798. begin
  799. DocInfo := TDocInfo.Create;
  800. DocInfos.Add(DocInfo);
  801. DocInfo.Element := AElement;
  802. DocInfo.Filename := AFilename;
  803. end;
  804. end;
  805. }
  806. { Used for:
  807. - <link> elements in descriptions
  808. - "see also" entries
  809. - AppendHyperlink (for unresolved parse tree element links)
  810. }
  811. function THTMLWriter.ResolveLinkIDInUnit(const Name,AUnitName: String): DOMString;
  812. begin
  813. Result:=ResolveLinkID(Name);
  814. If (Result='') and (AUnitName<>'') then
  815. Result:=ResolveLinkID(AUnitName+'.'+Name);
  816. end;
  817. function THTMLWriter.ResolveLinkID(const Name: String; Level : Integer = 0): DOMString;
  818. var
  819. i: Integer;
  820. ThisPackage: TLinkNode;
  821. begin
  822. Result:=Engine.ResolveLink(Module,Name, False);
  823. if Length(Result) > 0 then
  824. if Copy(Result, 1, Length(CurDirectory) + 1) = CurDirectory + '/' then
  825. Result := Copy(Result, Length(CurDirectory) + 2, Length(Result))
  826. else if not IsLinkAbsolute(Result) then
  827. Result := BaseDirectory + Result;
  828. end;
  829. function THTMLWriter.ResolveLinkWithinPackage(AElement: TPasElement;
  830. ASubpageIndex: Integer): String;
  831. var
  832. ParentEl: TPasElement;
  833. begin
  834. ParentEl := AElement;
  835. while Assigned(ParentEl) and not (ParentEl.ClassType = TPasPackage) do
  836. ParentEl := ParentEl.Parent;
  837. if Assigned(ParentEl) and (TPasPackage(ParentEl) = Engine.Package) then
  838. begin
  839. Result := Allocator.GetFilename(AElement, ASubpageIndex);
  840. if Copy(Result, 1, Length(CurDirectory) + 1) = CurDirectory + '/' then
  841. Result := Copy(Result, Length(CurDirectory) + 2, Length(Result))
  842. else
  843. Result := BaseDirectory + Result;
  844. end else
  845. SetLength(Result, 0);
  846. end;
  847. function THTMLWriter.CreateEl(Parent: TDOMNode;
  848. const AName: DOMString): THTMLElement;
  849. begin
  850. Result := Doc.CreateElement(AName);
  851. Parent.AppendChild(Result);
  852. end;
  853. function THTMLWriter.CreatePara(Parent: TDOMNode): THTMLElement;
  854. begin
  855. Result := CreateEl(Parent, 'p');
  856. end;
  857. function THTMLWriter.CreateH1(Parent: TDOMNode): THTMLElement;
  858. begin
  859. Result := CreateEl(Parent, 'h1');
  860. end;
  861. function THTMLWriter.CreateH2(Parent: TDOMNode): THTMLElement;
  862. begin
  863. Result := CreateEl(Parent, 'h2');
  864. end;
  865. function THTMLWriter.CreateH3(Parent: TDOMNode): THTMLElement;
  866. begin
  867. Result := CreateEl(Parent, 'h3');
  868. end;
  869. function THTMLWriter.CreateTable(Parent: TDOMNode; const AClass: DOMString = ''): THTMLElement;
  870. begin
  871. Result := CreateEl(Parent, 'table');
  872. Result['cellspacing'] := '0';
  873. Result['cellpadding'] := '0';
  874. if AClass <> '' then
  875. Result['class'] := AClass;
  876. end;
  877. function THTMLWriter.CreateContentTable(Parent: TDOMNode): THTMLElement;
  878. begin
  879. Result := CreateEl(Parent, 'table');
  880. end;
  881. function THTMLWriter.CreateTR(Parent: TDOMNode): THTMLElement;
  882. begin
  883. Result := CreateEl(Parent, 'tr');
  884. end;
  885. function THTMLWriter.CreateTD(Parent: TDOMNode): THTMLElement;
  886. begin
  887. Result := CreateEl(Parent, 'td');
  888. end;
  889. function THTMLWriter.CreateTD_vtop(Parent: TDOMNode): THTMLElement;
  890. begin
  891. Result := CreateEl(Parent, 'td');
  892. Result['valign'] := 'top';
  893. end;
  894. function THTMLWriter.CreateLink(Parent: TDOMNode;
  895. const AHRef: DOMString): THTMLElement;
  896. begin
  897. Result := CreateEl(Parent, 'a');
  898. Result['href'] := FixHtmlPath(AHRef);
  899. end;
  900. function THTMLWriter.CreateAnchor(Parent: TDOMNode;
  901. const AName: DOMString): THTMLElement;
  902. begin
  903. Result := CreateEl(Parent, 'a');
  904. Result['name'] := AName;
  905. end;
  906. function THTMLWriter.CreateCode(Parent: TDOMNode): THTMLElement;
  907. begin
  908. Result := CreateEl(CreateEl(Parent, 'tt'), 'span');
  909. Result['class'] := 'code';
  910. end;
  911. function THTMLWriter.CreateWarning(Parent: TDOMNode): THTMLElement;
  912. begin
  913. Result := CreateEl(Parent, 'span');
  914. Result['class'] := 'warning';
  915. end;
  916. procedure THTMLWriter.DescrEmitNotesHeader(AContext: TPasElement);
  917. begin
  918. AppendText(CreateH2(BodyElement), SDocNotes);
  919. PushOutputNode(BodyElement);
  920. end;
  921. procedure THTMLWriter.DescrEmitNotesFooter(AContext: TPasElement);
  922. begin
  923. PopOutPutNode;
  924. end;
  925. procedure THTMLWriter.PushOutputNode(ANode: TDOMNode);
  926. begin
  927. OutputNodeStack.Add(CurOutputNode);
  928. CurOutputNode := ANode;
  929. end;
  930. procedure THTMLWriter.PopOutputNode;
  931. begin
  932. CurOutputNode := TDOMNode(OutputNodeStack[OutputNodeStack.Count - 1]);
  933. OutputNodeStack.Delete(OutputNodeStack.Count - 1);
  934. end;
  935. procedure THTMLWriter.DescrWriteText(const AText: DOMString);
  936. begin
  937. AppendText(CurOutputNode, AText);
  938. end;
  939. procedure THTMLWriter.DescrBeginBold;
  940. begin
  941. PushOutputNode(CreateEl(CurOutputNode, 'b'));
  942. end;
  943. procedure THTMLWriter.DescrEndBold;
  944. begin
  945. PopOutputNode;
  946. end;
  947. procedure THTMLWriter.DescrBeginItalic;
  948. begin
  949. PushOutputNode(CreateEl(CurOutputNode, 'i'));
  950. end;
  951. procedure THTMLWriter.DescrEndItalic;
  952. begin
  953. PopOutputNode;
  954. end;
  955. procedure THTMLWriter.DescrBeginEmph;
  956. begin
  957. PushOutputNode(CreateEl(CurOutputNode, 'em'));
  958. end;
  959. procedure THTMLWriter.DescrEndEmph;
  960. begin
  961. PopOutputNode;
  962. end;
  963. procedure THTMLWriter.DescrWriteImageEl(const AFileName, ACaption, ALinkName : DOMString);
  964. Var
  965. Pel,Cel,Lel : TDOMNode;
  966. El :TDomElement;
  967. D : String;
  968. L : Integer;
  969. begin
  970. // Determine parent node.
  971. If (ACaption='') then
  972. Pel:=CurOutputNode
  973. else
  974. begin
  975. Cel:=CreateTable(CurOutputNode, 'imagetable');
  976. Pel:=CreateTD(CreateTR(Cel));
  977. Cel:=CreateTD(CreateTR(Cel));
  978. El := CreateEl(Cel, 'span');
  979. El['class'] := 'imagecaption';
  980. Cel := El;
  981. If (ALinkName<>'') then
  982. Cel:=CreateAnchor(Cel,ALinkName);
  983. AppendText(Cel,ACaption);
  984. end;
  985. // Determine URL for image.
  986. If (Module=Nil) then
  987. D:=Allocator.GetRelativePathToTop(Package)
  988. else
  989. D:=Allocator.GetRelativePathToTop(Module);
  990. L:=Length(D);
  991. If (L>0) and (D[L]<>'/') then
  992. D:=D+'/';
  993. // Create image node.
  994. El:=CreateEl(Pel,'img');
  995. EL['src']:=D + BaseImageURL + AFileName;
  996. El['alt']:=ACaption;
  997. //cache image filename, so it can be used later (CHM)
  998. FImageFileList.Add(BaseImageURL + AFileName);
  999. end;
  1000. procedure THTMLWriter.DescrWriteFileEl(const AText: DOMString);
  1001. var
  1002. NewEl: TDOMElement;
  1003. begin
  1004. NewEl := CreateEl(CurOutputNode, 'span');
  1005. NewEl['class'] := 'file';
  1006. AppendText(NewEl, AText);
  1007. end;
  1008. procedure THTMLWriter.DescrWriteKeywordEl(const AText: DOMString);
  1009. var
  1010. NewEl: TDOMElement;
  1011. begin
  1012. NewEl := CreateEl(CurOutputNode, 'span');
  1013. NewEl['class'] := 'kw';
  1014. AppendText(NewEl, AText);
  1015. end;
  1016. procedure THTMLWriter.DescrWriteVarEl(const AText: DOMString);
  1017. begin
  1018. AppendText(CreateEl(CurOutputNode, 'var'), AText);
  1019. end;
  1020. procedure THTMLWriter.DescrBeginLink(const AId: DOMString);
  1021. var
  1022. a,s,n : String;
  1023. begin
  1024. a:=AId;
  1025. s := ResolveLinkID(a);
  1026. if Length(s) = 0 then
  1027. begin
  1028. if assigned(module) then
  1029. s:=module.name
  1030. else
  1031. s:='?';
  1032. if a='' then a:='<empty>';
  1033. if Assigned(CurrentContext) then
  1034. N:=CurrentContext.Name
  1035. else
  1036. N:='?';
  1037. DoLog(SErrUnknownLinkID, [s,n,a]);
  1038. PushOutputNode(CreateEl(CurOutputNode, 'b'));
  1039. end else
  1040. PushOutputNode(CreateLink(CurOutputNode, s));
  1041. end;
  1042. procedure THTMLWriter.DescrEndLink;
  1043. begin
  1044. PopOutputNode;
  1045. end;
  1046. procedure THTMLWriter.DescrBeginURL(const AURL: DOMString);
  1047. begin
  1048. PushOutputNode(CreateLink(CurOutputNode, AURL));
  1049. end;
  1050. procedure THTMLWriter.DescrEndURL;
  1051. begin
  1052. PopOutputNode;
  1053. end;
  1054. procedure THTMLWriter.DescrWriteLinebreak;
  1055. begin
  1056. CreateEl(CurOutputNode, 'br');
  1057. end;
  1058. procedure THTMLWriter.DescrBeginParagraph;
  1059. begin
  1060. PushOutputNode(CreatePara(CurOutputNode));
  1061. end;
  1062. procedure THTMLWriter.DescrEndParagraph;
  1063. begin
  1064. PopOutputNode;
  1065. end;
  1066. procedure THTMLWriter.DescrBeginCode(HasBorder: Boolean; const AHighlighterName: String);
  1067. begin
  1068. DoPasHighlighting := (AHighlighterName = '') or (AHighlighterName = 'Pascal');
  1069. HighlighterFlags := 0;
  1070. PushOutputNode(CreateEl(CurOutputNode, 'pre'));
  1071. end;
  1072. procedure THTMLWriter.DescrWriteCodeLine(const ALine: String);
  1073. begin
  1074. if DoPasHighlighting then
  1075. begin
  1076. HighlighterFlags := AppendPasSHFragment(CurOutputNode, ALine,
  1077. HighlighterFlags);
  1078. AppendText(CurOutputNode, #10);
  1079. end else
  1080. AppendText(CurOutputNode, ALine + #10);
  1081. end;
  1082. procedure THTMLWriter.DescrEndCode;
  1083. begin
  1084. PopOutputNode;
  1085. end;
  1086. procedure THTMLWriter.DescrBeginOrderedList;
  1087. begin
  1088. PushOutputNode(CreateEl(CurOutputNode, 'ol'));
  1089. end;
  1090. procedure THTMLWriter.DescrEndOrderedList;
  1091. begin
  1092. PopOutputNode;
  1093. end;
  1094. procedure THTMLWriter.DescrBeginUnorderedList;
  1095. begin
  1096. PushOutputNode(CreateEl(CurOutputNode, 'ul'));
  1097. end;
  1098. procedure THTMLWriter.DescrEndUnorderedList;
  1099. begin
  1100. PopOutputNode;
  1101. end;
  1102. procedure THTMLWriter.DescrBeginDefinitionList;
  1103. begin
  1104. PushOutputNode(CreateEl(CurOutputNode, 'dl'));
  1105. end;
  1106. procedure THTMLWriter.DescrEndDefinitionList;
  1107. begin
  1108. PopOutputNode;
  1109. end;
  1110. procedure THTMLWriter.DescrBeginListItem;
  1111. begin
  1112. PushOutputNode(CreateEl(CurOutputNode, 'li'));
  1113. end;
  1114. procedure THTMLWriter.DescrEndListItem;
  1115. begin
  1116. PopOutputNode;
  1117. end;
  1118. procedure THTMLWriter.DescrBeginDefinitionTerm;
  1119. begin
  1120. PushOutputNode(CreateEl(CurOutputNode, 'dt'));
  1121. end;
  1122. procedure THTMLWriter.DescrEndDefinitionTerm;
  1123. begin
  1124. PopOutputNode;
  1125. end;
  1126. procedure THTMLWriter.DescrBeginDefinitionEntry;
  1127. begin
  1128. PushOutputNode(CreateEl(CurOutputNode, 'dd'));
  1129. end;
  1130. procedure THTMLWriter.DescrEndDefinitionEntry;
  1131. begin
  1132. PopOutputNode;
  1133. end;
  1134. procedure THTMLWriter.DescrBeginSectionTitle;
  1135. begin
  1136. PushOutputNode(CreateEl(CurOutputNode, 'h3'));
  1137. end;
  1138. procedure THTMLWriter.DescrBeginSectionBody;
  1139. begin
  1140. PopOutputNode;
  1141. end;
  1142. procedure THTMLWriter.DescrEndSection;
  1143. begin
  1144. end;
  1145. procedure THTMLWriter.DescrBeginRemark;
  1146. var
  1147. NewEl, TDEl: TDOMElement;
  1148. begin
  1149. NewEl := CreateEl(CurOutputNode, 'table');
  1150. NewEl['width'] := '100%';
  1151. NewEl['border'] := '0';
  1152. NewEl['CellSpacing'] := '0';
  1153. NewEl['class'] := 'remark';
  1154. NewEl := CreateTR(NewEl);
  1155. TDEl := CreateTD(NewEl);
  1156. TDEl['valign'] := 'top';
  1157. TDEl['class'] := 'pre';
  1158. AppendText(CreateEl(TDEl, 'b'), SDocRemark);
  1159. PushOutputNode(CreateTD(NewEl));
  1160. end;
  1161. procedure THTMLWriter.DescrEndRemark;
  1162. begin
  1163. PopOutputNode;
  1164. end;
  1165. procedure THTMLWriter.DescrBeginTable(ColCount: Integer; HasBorder: Boolean);
  1166. var
  1167. Table: TDOMElement;
  1168. begin
  1169. Table := CreateEl(CurOutputNode, 'table');
  1170. Table['border'] := IntToStr(Ord(HasBorder));
  1171. PushOutputNode(Table);
  1172. end;
  1173. procedure THTMLWriter.DescrEndTable;
  1174. begin
  1175. PopOutputNode;
  1176. end;
  1177. procedure THTMLWriter.DescrBeginTableCaption;
  1178. begin
  1179. PushOutputNode(CreateEl(CurOutputNode, 'caption'));
  1180. end;
  1181. procedure THTMLWriter.DescrEndTableCaption;
  1182. begin
  1183. PopOutputNode;
  1184. end;
  1185. procedure THTMLWriter.DescrBeginTableHeadRow;
  1186. begin
  1187. PushOutputNode(CreateTr(CurOutputNode));
  1188. InsideHeadRow := True;
  1189. end;
  1190. procedure THTMLWriter.DescrEndTableHeadRow;
  1191. begin
  1192. InsideHeadRow := False;
  1193. PopOutputNode;
  1194. end;
  1195. procedure THTMLWriter.DescrBeginTableRow;
  1196. begin
  1197. PushOutputNode(CreateTR(CurOutputNode));
  1198. end;
  1199. procedure THTMLWriter.DescrEndTableRow;
  1200. begin
  1201. PopOutputNode;
  1202. end;
  1203. procedure THTMLWriter.DescrBeginTableCell;
  1204. begin
  1205. if InsideHeadRow then
  1206. PushOutputNode(CreateEl(CurOutputNode, 'th'))
  1207. else
  1208. PushOutputNode(CreateTD(CurOutputNode));
  1209. end;
  1210. procedure THTMLWriter.DescrEndTableCell;
  1211. begin
  1212. PopOutputNode;
  1213. end;
  1214. procedure THTMLWriter.AppendText(Parent: TDOMNode; const AText: DOMString);
  1215. begin
  1216. Parent.AppendChild(Doc.CreateTextNode(AText));
  1217. end;
  1218. procedure THTMLWriter.AppendNbSp(Parent: TDOMNode; ACount: Integer);
  1219. begin
  1220. while ACount > 0 do
  1221. begin
  1222. Parent.AppendChild(Doc.CreateEntityReference('nbsp'));
  1223. Dec(ACount);
  1224. end;
  1225. end;
  1226. procedure THTMLWriter.AppendSym(Parent: TDOMNode; const AText: DOMString);
  1227. var
  1228. El: TDOMElement;
  1229. begin
  1230. El := CreateEl(Parent, 'span');
  1231. El['class'] := 'sym';
  1232. AppendText(El, AText);
  1233. end;
  1234. procedure THTMLWriter.AppendKw(Parent: TDOMNode; const AText: DOMString);
  1235. var
  1236. El: TDOMElement;
  1237. begin
  1238. El := CreateEl(Parent, 'span');
  1239. El['class'] := 'kw';
  1240. AppendText(El, AText);
  1241. end;
  1242. function THTMLWriter.AppendPasSHFragment(Parent: TDOMNode;
  1243. const AText: String; AShFlags: Byte): Byte;
  1244. var
  1245. Line, Last, p: PChar;
  1246. IsInSpecial: Boolean;
  1247. lastwasasm : boolean;
  1248. El: TDOMElement;
  1249. Procedure MaybeOutput;
  1250. Var
  1251. CurParent: TDomNode;
  1252. begin
  1253. If (Last<>Nil) then
  1254. begin
  1255. If (el<>Nil) then
  1256. CurParent:=El
  1257. else
  1258. CurParent:=Parent;
  1259. AppendText(CurParent,Last);
  1260. El:=Nil;
  1261. Last:=Nil;
  1262. end;
  1263. end;
  1264. Function NewEl(Const ElType,Attr,AttrVal : String) : TDomElement;
  1265. begin
  1266. Result:=CreateEl(Parent,ElType);
  1267. Result[Attr]:=AttrVal;
  1268. end;
  1269. Function NewSpan(Const AttrVal : String) : TDomElement;
  1270. begin
  1271. Result:=CreateEl(Parent,'span');
  1272. Result['class']:=AttrVal;
  1273. end;
  1274. begin
  1275. GetMem(Line, Length(AText) * 3 + 4);
  1276. Try
  1277. DoPascalHighlighting(AShFlags, PChar(AText), Line);
  1278. Result := AShFlags;
  1279. IsInSpecial := False;
  1280. Last := Nil;
  1281. p := Line;
  1282. el:=nil;
  1283. while p[0] <> #0 do
  1284. begin
  1285. if p[0] = LF_ESCAPE then
  1286. begin
  1287. p[0] := #0;
  1288. MaybeOutput;
  1289. case Ord(p[1]) of
  1290. shDefault: El:=Nil;
  1291. shInvalid: El:=newel('font','color','red');
  1292. shSymbol : El:=newspan('sym');
  1293. shKeyword: El:=newspan('kw');
  1294. shComment: El:=newspan('cmt');
  1295. shDirective: El:=newspan('dir');
  1296. shNumbers: El:=newspan('num');
  1297. shCharacters: El:=newspan('chr');
  1298. shStrings: El:=newspan('str');
  1299. shAssembler: El:=newspan('asm');
  1300. end;
  1301. Inc(P);
  1302. end
  1303. else If (Last=Nil) then
  1304. Last:=P;
  1305. Inc(p);
  1306. end;
  1307. MaybeOutput;
  1308. Finally
  1309. FreeMem(Line);
  1310. end;
  1311. end;
  1312. Procedure THTMLWriter.AppendShortDescr(AContext: TPasElement; Parent: TDOMNode; DocNode : TDocNode);
  1313. Var
  1314. N : TDocNode;
  1315. begin
  1316. if Assigned(DocNode) then
  1317. begin
  1318. If (DocNode.Link<>'') then
  1319. begin
  1320. N:=Engine.FindLinkedNode(DocNode);
  1321. If (N<>Nil) then
  1322. DocNode:=N;
  1323. end;
  1324. If Assigned(DocNode.ShortDescr) then
  1325. begin
  1326. PushOutputNode(Parent);
  1327. try
  1328. if not ConvertShort(AContext,TDomElement(DocNode.ShortDescr)) then
  1329. Warning(AContext, SErrInvalidShortDescr)
  1330. finally
  1331. PopOutputNode;
  1332. end;
  1333. end;
  1334. end;
  1335. end;
  1336. procedure THTMLWriter.AppendShortDescr(Parent: TDOMNode; Element: TPasElement);
  1337. begin
  1338. AppendShortDescr(Element,Parent,Engine.FindDocNode(Element));
  1339. end;
  1340. procedure THTMLWriter.AppendShortDescrCell(Parent: TDOMNode;
  1341. Element: TPasElement);
  1342. var
  1343. ParaEl: TDOMElement;
  1344. begin
  1345. if Assigned(Engine.FindShortDescr(Element)) then
  1346. begin
  1347. AppendNbSp(CreatePara(CreateTD(Parent)), 2);
  1348. ParaEl := CreatePara(CreateTD(Parent));
  1349. ParaEl['class'] := 'cmt';
  1350. AppendShortDescr(ParaEl, Element);
  1351. end;
  1352. end;
  1353. procedure THTMLWriter.AppendDescr(AContext: TPasElement; Parent: TDOMNode;
  1354. DescrNode: TDOMElement; AutoInsertBlock: Boolean);
  1355. begin
  1356. if Assigned(DescrNode) then
  1357. begin
  1358. PushOutputNode(Parent);
  1359. try
  1360. ConvertDescr(AContext, DescrNode, AutoInsertBlock);
  1361. finally
  1362. PopOutputNode;
  1363. end;
  1364. end;
  1365. end;
  1366. procedure THTMLWriter.AppendDescrSection(AContext: TPasElement;
  1367. Parent: TDOMNode; DescrNode: TDOMElement; const ATitle: DOMString);
  1368. begin
  1369. if not IsDescrNodeEmpty(DescrNode) then
  1370. begin
  1371. If (ATitle<>'') then // Can be empty for topic.
  1372. AppendText(CreateH2(Parent), ATitle);
  1373. AppendDescr(AContext, Parent, DescrNode, True);
  1374. end;
  1375. end;
  1376. function THTMLWriter.AppendHyperlink(Parent: TDOMNode;
  1377. Element: TPasElement): TDOMElement;
  1378. var
  1379. s: String;
  1380. UnitList: TFPList;
  1381. i: Integer;
  1382. ThisPackage: TLinkNode;
  1383. begin
  1384. if Assigned(Element) then
  1385. begin
  1386. if Element.InheritsFrom(TPasUnresolvedTypeRef) then
  1387. begin
  1388. s := ResolveLinkID(Element.Name);
  1389. if Length(s) = 0 then
  1390. begin
  1391. { Try all packages }
  1392. ThisPackage := Engine.RootLinkNode.FirstChild;
  1393. while Assigned(ThisPackage) do
  1394. begin
  1395. s := ResolveLinkID(ThisPackage.Name + '.' + Element.Name);
  1396. if Length(s) > 0 then
  1397. break;
  1398. ThisPackage := ThisPackage.NextSibling;
  1399. end;
  1400. if Length(s) = 0 then
  1401. begin
  1402. { Okay, then we have to try all imported units of the current module }
  1403. UnitList := Module.InterfaceSection.UsesList;
  1404. for i := UnitList.Count - 1 downto 0 do
  1405. begin
  1406. { Try all packages }
  1407. ThisPackage := Engine.RootLinkNode.FirstChild;
  1408. while Assigned(ThisPackage) do
  1409. begin
  1410. s := ResolveLinkID(ThisPackage.Name + '.' +
  1411. TPasType(UnitList[i]).Name + '.' + Element.Name);
  1412. if Length(s) > 0 then
  1413. break;
  1414. ThisPackage := ThisPackage.NextSibling;
  1415. end;
  1416. if length(s)=0 then
  1417. s := ResolveLinkID('#rtl.System.' + Element.Name);
  1418. if Length(s) > 0 then
  1419. break;
  1420. end;
  1421. end;
  1422. end;
  1423. end else if Element is TPasEnumValue then
  1424. s := ResolveLinkID(Element.Parent.PathName)
  1425. else
  1426. s := ResolveLinkID(Element.PathName);
  1427. if Length(s) > 0 then
  1428. begin
  1429. Result := CreateLink(Parent, s);
  1430. AppendText(Result, Element.Name);
  1431. end else
  1432. begin
  1433. Result := nil;
  1434. AppendText(Parent, Element.Name);
  1435. end;
  1436. end else
  1437. begin
  1438. Result := nil;
  1439. AppendText(CreateWarning(Parent), '<NIL>');
  1440. end;
  1441. end;
  1442. { Returns the new CodeEl, which will be the old CodeEl in most cases }
  1443. function THTMLWriter.AppendType(CodeEl, TableEl: TDOMElement;
  1444. Element: TPasType; Expanded: Boolean; NestingLevel: Integer): TDOMElement;
  1445. Var
  1446. S : String;
  1447. begin
  1448. Result := CodeEl;
  1449. if not Assigned(Element) then
  1450. AppendText(CreateWarning(CodeEl), '<NIL>')
  1451. else if (not Expanded) and (Length(Element.Name) > 0) then
  1452. AppendHyperlink(CodeEl, Element)
  1453. else
  1454. // Array
  1455. if Element.ClassType = TPasArrayType then
  1456. begin
  1457. S:='array ';
  1458. If (TPasArrayType(Element).IndexRange<>'') then
  1459. S:=S+'[' + TPasArrayType(Element).IndexRange + '] ';
  1460. S:=S+'of ';
  1461. If (TPasArrayType(Element).ElType=Nil) then
  1462. S:=S+'Const';
  1463. AppendPasSHFragment(CodeEl,S,0);
  1464. If (TPasArrayType(Element).ElType<>Nil) then
  1465. Result := AppendType(CodeEl, TableEl, TPasArrayType(Element).ElType, False);
  1466. end else
  1467. // Procedure or funtion type
  1468. if Element.InheritsFrom(TPasProcedureType) then
  1469. begin
  1470. AppendKw(CodeEl, TPasProcedureType(Element).TypeName);
  1471. Result := AppendProcType(CodeEl, TableEl, TPasProcedureType(Element), 0)
  1472. end else
  1473. // Range type
  1474. if Element.InheritsFrom(TPasRangeType) then
  1475. AppendPasSHFragment(CodeEl, TPasRangeType(Element).RangeStart + '..' +
  1476. TPasRangeType(Element).RangeEnd, 0)
  1477. // Record type
  1478. else if Element.ClassType = TPasRecordType then
  1479. Result := AppendRecordType(CodeEl, TableEl, TPasRecordType(Element), NestingLevel)
  1480. else if (Element.ClassType = TPasFileType) and (TPasFileType(Element).elType=Nil) then
  1481. AppendPasSHFragment(CodeEl,'file',0)
  1482. else
  1483. // Other types
  1484. AppendHyperlink(CodeEl, Element);
  1485. end;
  1486. function THTMLWriter.AppendProcType(CodeEl, TableEl: TDOMElement;
  1487. Element: TPasProcedureType; Indent: Integer): TDOMElement;
  1488. function CreateIndentedCodeEl(Indent: Integer): TDOMElement;
  1489. begin
  1490. Result := CreateCode(CreatePara(CreateTD(CreateTR(TableEl))));
  1491. AppendNbSp(Result, Indent);
  1492. end;
  1493. var
  1494. i: Integer;
  1495. Arg: TPasArgument;
  1496. begin
  1497. if Element.Args.Count > 0 then
  1498. begin
  1499. AppendSym(CodeEl, '(');
  1500. for i := 0 to Element.Args.Count - 1 do
  1501. begin
  1502. Arg := TPasArgument(Element.Args[i]);
  1503. CodeEl := CreateIndentedCodeEl(Indent + 2);
  1504. case Arg.Access of
  1505. argConst: AppendKw(CodeEl, 'const ');
  1506. argVar: AppendKw(CodeEl, 'var ');
  1507. argOut: AppendKw(CodeEl, 'out ');
  1508. end;
  1509. AppendText(CodeEl, Arg.Name);
  1510. if Assigned(Arg.ArgType) then
  1511. begin
  1512. AppendSym(CodeEl, ': ');
  1513. CodeEl := AppendType(CodeEl, TableEl, Arg.ArgType, False);
  1514. end;
  1515. if Length(Arg.Value) > 0 then
  1516. AppendPasSHFragment(CodeEl, ' = ' + Arg.Value, 0);
  1517. if i < Element.Args.Count - 1 then
  1518. AppendSym(CodeEl, ';');
  1519. end;
  1520. if Element.InheritsFrom(TPasFunctionType) or Element.IsOfObject then
  1521. begin
  1522. CodeEl := CreateIndentedCodeEl(Indent);
  1523. if Element.InheritsFrom(TPasFunctionType) then
  1524. begin
  1525. AppendSym(CodeEl, '):');
  1526. AppendHyperlink(CodeEl, TPasFunctionType(Element).ResultEl.ResultType);
  1527. end else
  1528. AppendSym(CodeEl, ')');
  1529. if Element.IsOfObject then
  1530. begin
  1531. AppendText(CodeEl, ' '); // Don't remove
  1532. AppendKw(CodeEl, 'of object');
  1533. end;
  1534. end else
  1535. if Indent > 0 then
  1536. AppendSym(CodeEl, ')')
  1537. else
  1538. begin
  1539. CodeEl := CreateCode(CreatePara(CreateTD(CreateTR(TableEl))));
  1540. AppendSym(CodeEl, ')');
  1541. end;
  1542. end else
  1543. begin
  1544. { Procedure or function without arguments }
  1545. if Element.InheritsFrom(TPasFunctionType) then
  1546. begin
  1547. AppendSym(CodeEl, ': ');
  1548. AppendHyperlink(CodeEl, TPasFunctionType(Element).ResultEl.ResultType);
  1549. end;
  1550. if Element.IsOfObject then
  1551. AppendKw(CodeEl, ' of object');
  1552. end;
  1553. Result := CodeEl;
  1554. end;
  1555. procedure THTMLWriter.AppendProcExt(CodeEl: TDOMElement;
  1556. Element: TPasProcedure);
  1557. procedure AppendExt(const Ext: String);
  1558. begin
  1559. AppendKw(CodeEl, ' ' + Ext);
  1560. AppendSym(CodeEl, ';');
  1561. end;
  1562. begin
  1563. if Element.IsVirtual then
  1564. AppendExt('virtual');
  1565. if Element.IsDynamic then
  1566. AppendExt('dynamic');
  1567. if Element.IsAbstract then
  1568. AppendExt('abstract');
  1569. if Element.IsOverride then
  1570. AppendExt('override');
  1571. if Element.IsOverload then
  1572. AppendExt('overload');
  1573. if Element.IsMessage then
  1574. AppendExt('message');
  1575. end;
  1576. { Used in two places:
  1577. - Page for the method of a class
  1578. - Page for a tandalone procedure or function. }
  1579. procedure THTMLWriter.AppendProcDecl(CodeEl, TableEl: TDOMElement;
  1580. Element: TPasProcedureBase);
  1581. procedure WriteVariant(AProc: TPasProcedure; SkipResult : Boolean);
  1582. begin
  1583. AppendProcArgsSection(TableEl.ParentNode, AProc.ProcType, SkipResult);
  1584. AppendKw(CodeEl, AProc.TypeName);
  1585. if Element.Parent.ClassType = TPasClassType then
  1586. begin
  1587. AppendText(CodeEl, ' ');
  1588. AppendHyperlink(CodeEl, Element.Parent);
  1589. AppendSym(CodeEl, '.');
  1590. AppendText(CodeEl, AProc.Name);
  1591. end else
  1592. AppendText(CodeEl, ' ' + AProc.FullName);
  1593. CodeEl := AppendProcType(CodeEl, TableEl, AProc.ProcType, 0);
  1594. AppendSym(CodeEl, ';');
  1595. AppendProcExt(CodeEl, AProc);
  1596. end;
  1597. var
  1598. i,fc: Integer;
  1599. P : TPasProcedure;
  1600. begin
  1601. fc:=0;
  1602. if Element.ClassType = TPasOverloadedProc then
  1603. for i := 0 to TPasOverloadedProc(Element).Overloads.Count - 1 do
  1604. begin
  1605. P:=TPasProcedure(TPasOverloadedProc(Element).Overloads[i]);
  1606. if (P.ProcType is TPasFunctionType) then
  1607. Inc(fc);
  1608. if i > 0 then
  1609. begin
  1610. CreateEl(CodeEl, 'br');
  1611. CreateEl(CodeEl, 'br');
  1612. end;
  1613. WriteVariant(P,fc>1);
  1614. end
  1615. else
  1616. WriteVariant(TPasProcedure(Element),False);
  1617. end;
  1618. procedure THTMLWriter.AppendProcArgsSection(Parent: TDOMNode;
  1619. Element: TPasProcedureType; SkipResult : Boolean = False);
  1620. var
  1621. HasFullDescr, IsFirst: Boolean;
  1622. ResultEl: TPasResultElement;
  1623. ArgTableEl, TREl: TDOMElement;
  1624. DocNode: TDocNode;
  1625. i: Integer;
  1626. Arg: TPasArgument;
  1627. begin
  1628. IsFirst := True;
  1629. for i := 0 to Element.Args.Count - 1 do
  1630. begin
  1631. Arg := TPasArgument(Element.Args[i]);
  1632. if IsDescrNodeEmpty(Engine.FindShortDescr(Arg)) then
  1633. continue;
  1634. if IsFirst then
  1635. begin
  1636. IsFirst := False;
  1637. AppendText(CreateH2(Parent), SDocArguments);
  1638. ArgTableEl := CreateTable(Parent);
  1639. end;
  1640. TREl := CreateTR(ArgTableEl);
  1641. AppendText(CreateCode(CreatePara(CreateTD_vtop(TREl))), Arg.Name);
  1642. AppendShortDescrCell(TREl, Arg);
  1643. end;
  1644. if (Element.ClassType = TPasFunctionType) and not SkipResult then
  1645. begin
  1646. ResultEl := TPasFunctionType(Element).ResultEl;
  1647. DocNode := Engine.FindDocNode(ResultEl);
  1648. HasFullDescr := Assigned(DocNode) and not IsDescrNodeEmpty(DocNode.Descr);
  1649. if HasFullDescr or
  1650. (Assigned(DocNode) and not IsDescrNodeEmpty(DocNode.ShortDescr)) then
  1651. begin
  1652. AppendText(CreateH2(Parent), SDocFunctionResult);
  1653. if HasFullDescr then
  1654. AppendDescr(ResultEl, Parent, DocNode.Descr, True)
  1655. else
  1656. AppendDescr(ResultEl, CreatePara(Parent), DocNode.ShortDescr, False);
  1657. end;
  1658. end;
  1659. end;
  1660. function THTMLWriter.AppendRecordType(CodeEl, TableEl: TDOMElement;
  1661. Element: TPasRecordType; NestingLevel: Integer): TDOMElement;
  1662. var
  1663. i, j: Integer;
  1664. Variable: TPasVariable;
  1665. TREl, TDEl: TDOMElement;
  1666. CurVariant: TPasVariant;
  1667. begin
  1668. if not (Element.Parent is TPasVariant) then
  1669. if Element.IsPacked then
  1670. If Element.IsBitPacked then
  1671. AppendKw(CodeEl, 'bitpacked record')
  1672. else
  1673. AppendKW(CodeEl, 'packed record')
  1674. else
  1675. AppendKw(CodeEl, 'record');
  1676. for i := 0 to Element.Members.Count - 1 do
  1677. begin
  1678. Variable := TPasVariable(Element.Members[i]);
  1679. TREl := CreateTR(TableEl);
  1680. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  1681. AppendShortDescrCell(TREl, Variable);
  1682. AppendNbSp(CodeEl, NestingLevel * 2 + 2);
  1683. AppendText(CodeEl, Variable.Name);
  1684. AppendSym(CodeEl, ': ');
  1685. CodeEl := AppendType(CodeEl, TableEl, Variable.VarType, False, NestingLevel + 1);
  1686. AppendSym(CodeEl, ';');
  1687. end;
  1688. if Assigned(Element.VariantType) then
  1689. begin
  1690. TREl := CreateTR(TableEl);
  1691. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  1692. AppendNbSp(CodeEl, NestingLevel * 2 + 2);
  1693. AppendKw(CodeEl, 'case ');
  1694. if TPasRecordType(Element).VariantName <> '' then
  1695. begin
  1696. AppendText(CodeEl, TPasRecordType(Element).VariantName);
  1697. AppendSym(CodeEl, ': ');
  1698. end;
  1699. CodeEl := AppendType(CodeEl, TableEl, TPasRecordType(Element).VariantType, True);
  1700. AppendKw(CodeEl, ' of');
  1701. for i := 0 to TPasRecordType(Element).Variants.Count - 1 do
  1702. begin
  1703. CurVariant := TPasVariant(Element.Variants[i]);
  1704. TREl := CreateTR(TableEl);
  1705. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  1706. AppendNbSp(CodeEl, NestingLevel * 2 + 4);
  1707. for j := 0 to CurVariant.Values.Count - 1 do
  1708. begin
  1709. if j > 0 then
  1710. AppendSym(CodeEl, ', ');
  1711. AppendPasSHFragment(CodeEl, TPasElement(CurVariant.Values[j]).GetDeclaration(true), 0);
  1712. end;
  1713. AppendSym(CodeEl, ': (');
  1714. AppendType(CodeEl, TableEl, CurVariant.Members, True, NestingLevel + 3);
  1715. CodeEl := CreateCode(CreatePara(CreateTD_vtop(CreateTR(TableEl))));
  1716. AppendNbSp(CodeEl, NestingLevel * 2 + 6);
  1717. AppendSym(CodeEl, ');');
  1718. end;
  1719. end;
  1720. if not (Element.Parent is TPasVariant) then
  1721. begin
  1722. CodeEl := CreateCode(CreatePara(CreateTD(CreateTR(TableEl))));
  1723. AppendText(CodeEl, ' '); // !!!: Dirty trick, necessary for current XML writer
  1724. AppendNbSp(CodeEl, NestingLevel * 2);
  1725. AppendKw(CodeEl, 'end');
  1726. end;
  1727. Result := CodeEl;
  1728. end;
  1729. procedure THTMLWriter.AppendTitle(const AText: DOMString);
  1730. begin
  1731. AppendText(TitleElement, AText);
  1732. AppendText(CreateH1(BodyElement), AText);
  1733. end;
  1734. procedure THTMLWriter.AppendTopicMenuBar(Topic : TTopicElement);
  1735. var
  1736. TableEl, TREl, ParaEl, TitleEl: TDOMElement;
  1737. procedure AddLink(El : TPasElement; const AName: String);
  1738. begin
  1739. if FUseMenuBrackets then
  1740. AppendText(ParaEl, '[');
  1741. AppendText(CreateLink(ParaEl, ResolveLinkWithinPackage(El,0)),AName);
  1742. if FUseMenuBrackets then
  1743. AppendText(ParaEl, ']');
  1744. end;
  1745. begin
  1746. TableEl := CreateEl(BodyElement, 'table');
  1747. TableEl['cellpadding'] := '4';
  1748. TableEl['cellspacing'] := '0';
  1749. TableEl['border'] := '0';
  1750. TableEl['width'] := '100%';
  1751. TableEl['class'] := 'bar';
  1752. TREl := CreateTR(TableEl);
  1753. ParaEl := CreateEl(CreateTD(TREl), 'b');
  1754. If Assigned(Topic.Previous) then
  1755. AddLink(Topic.Previous,SDocPrevious);
  1756. If Assigned(Topic.Parent) then
  1757. AddLink(Topic.Parent,SDocUp);
  1758. if Assigned(Topic.Next) then
  1759. AddLink(Topic.Next,SDocNext);
  1760. if Length(SearchPage) > 0 then
  1761. begin
  1762. if FUseMenuBrackets then
  1763. AppendText(ParaEl, '[');
  1764. AppendText(CreateLink(ParaEl, SearchPage), SDocSearch);
  1765. if FUseMenuBrackets then
  1766. AppendText(ParaEl, ']');
  1767. end;
  1768. ParaEl := CreateTD(TREl);
  1769. ParaEl['align'] := 'right';
  1770. TitleEl := CreateEl(ParaEl, 'span');
  1771. TitleEl['class'] := 'bartitle';
  1772. if Assigned(Module) then
  1773. AppendText(TitleEl, Format(SDocUnitTitle, [Module.Name]));
  1774. if Assigned(Package) then
  1775. begin
  1776. AppendText(TitleEl, ' (');
  1777. AppendHyperlink(TitleEl, Package);
  1778. AppendText(TitleEl, ')');
  1779. end;
  1780. end;
  1781. procedure THTMLWriter.AppendMenuBar(ASubpageIndex: Integer);
  1782. var
  1783. TableEl, TREl, ParaEl, TitleEl: TDOMElement;
  1784. procedure AddLink(ALinkSubpageIndex: Integer; const AName: String);
  1785. begin
  1786. if FUseMenuBrackets then
  1787. AppendText(ParaEl, '[');
  1788. if ALinkSubpageIndex = ASubpageIndex then
  1789. AppendText(ParaEl, AName)
  1790. else
  1791. AppendText(
  1792. CreateLink(ParaEl, ResolveLinkWithinPackage(Module, ALinkSubpageIndex)),
  1793. AName);
  1794. if FUseMenuBrackets then
  1795. AppendText(ParaEl, ']');
  1796. end;
  1797. procedure AddPackageLink(ALinkSubpageIndex: Integer; const AName: String);
  1798. begin
  1799. if FUseMenuBrackets then
  1800. AppendText(ParaEl, '[');
  1801. if ALinkSubpageIndex = ASubpageIndex then
  1802. AppendText(ParaEl, AName)
  1803. else
  1804. AppendText(
  1805. CreateLink(ParaEl, ResolveLinkWithinPackage(Package, ALinkSubpageIndex)),
  1806. AName);
  1807. if FUseMenuBrackets then
  1808. AppendText(ParaEl, ']');
  1809. end;
  1810. begin
  1811. TableEl := CreateEl(BodyElement, 'table');
  1812. TableEl['cellpadding'] := '4';
  1813. TableEl['cellspacing'] := '0';
  1814. TableEl['border'] := '0';
  1815. TableEl['width'] := '100%';
  1816. TableEl['class'] := 'bar';
  1817. TREl := CreateTR(TableEl);
  1818. ParaEl := CreateEl(CreateTD(TREl), 'b');
  1819. if Assigned(Module) then
  1820. begin
  1821. AddLink(0, SDocOverview);
  1822. if Module.InterfaceSection.ResStrings.Count > 0 then
  1823. AddLink(ResstrSubindex, SDocResStrings);
  1824. if Module.InterfaceSection.Consts.Count > 0 then
  1825. AddLink(ConstsSubindex, SDocConstants);
  1826. if Module.InterfaceSection.Types.Count > 0 then
  1827. AddLink(TypesSubindex, SDocTypes);
  1828. if Module.InterfaceSection.Classes.Count > 0 then
  1829. AddLink(ClassesSubindex, SDocClasses);
  1830. if Module.InterfaceSection.Functions.Count > 0 then
  1831. AddLink(ProcsSubindex, SDocProceduresAndFunctions);
  1832. if Module.InterfaceSection.Variables.Count > 0 then
  1833. AddLink(VarsSubindex, SDocVariables);
  1834. AddLink(IndexSubIndex,SDocIdentifierIndex);
  1835. end
  1836. else
  1837. begin
  1838. AddPackageLink(IndexSubIndex, SDocIdentifierIndex);
  1839. AddPackageLink(ClassHierarchySubIndex, SDocPackageClassHierarchy);
  1840. end;
  1841. if Length(SearchPage) > 0 then
  1842. begin
  1843. if FUseMenuBrackets then
  1844. AppendText(ParaEl, '[');
  1845. AppendText(CreateLink(ParaEl, SearchPage), SDocSearch);
  1846. if FUseMenuBrackets then
  1847. AppendText(ParaEl, ']');
  1848. end;
  1849. ParaEl := CreateTD(TREl);
  1850. ParaEl['align'] := 'right';
  1851. TitleEl := CreateEl(ParaEl, 'span');
  1852. TitleEl['class'] := 'bartitle';
  1853. if Assigned(Module) then
  1854. AppendText(TitleEl, Format(SDocUnitTitle, [Module.Name]));
  1855. if Assigned(Package) then
  1856. begin
  1857. AppendText(TitleEl, ' (');
  1858. AppendHyperlink(TitleEl, Package);
  1859. AppendText(TitleEl, ')');
  1860. end;
  1861. end;
  1862. procedure THTMLWriter.AppendSourceRef(AElement: TPasElement);
  1863. begin
  1864. AppendText(CreatePara(BodyElement), Format(SDocSourcePosition,
  1865. [ExtractFileName(AElement.SourceFilename), AElement.SourceLinenumber]));
  1866. end;
  1867. Procedure THTMLWriter.AppendSeeAlsoSection(AElement : TPasElement;DocNode : TDocNode);
  1868. var
  1869. Node: TDOMNode;
  1870. TableEl, El, TREl, TDEl, ParaEl, NewEl, DescrEl: TDOMElement;
  1871. l,s,n: String;
  1872. f: Text;
  1873. IsFirstSeeAlso : Boolean;
  1874. begin
  1875. if Not (Assigned(DocNode) and Assigned(DocNode.SeeAlso)) then
  1876. Exit;
  1877. IsFirstSeeAlso := True;
  1878. Node:=DocNode.SeeAlso.FirstChild;
  1879. While Assigned(Node) do
  1880. begin
  1881. if (Node.NodeType=ELEMENT_NODE) and (Node.NodeName='link') then
  1882. begin
  1883. if IsFirstSeeAlso then
  1884. begin
  1885. IsFirstSeeAlso := False;
  1886. AppendText(CreateH2(BodyElement), SDocSeeAlso);
  1887. TableEl := CreateTable(BodyElement);
  1888. end;
  1889. El:=TDOMElement(Node);
  1890. TREl:=CreateTR(TableEl);
  1891. ParaEl:=CreatePara(CreateTD_vtop(TREl));
  1892. l:=El['id'];
  1893. s:= ResolveLinkID(l);
  1894. if Length(s)=0 then
  1895. begin
  1896. if assigned(module) then
  1897. s:=module.name
  1898. else
  1899. s:='?';
  1900. if l='' then l:='<empty>';
  1901. if Assigned(AElement) then
  1902. N:=AElement.Name
  1903. else
  1904. N:='?';
  1905. DoLog(SErrUnknownLinkID, [s,N,l]);
  1906. NewEl := CreateEl(ParaEl,'b')
  1907. end
  1908. else
  1909. NewEl := CreateLink(ParaEl,s);
  1910. if Not IsDescrNodeEmpty(El) then
  1911. begin
  1912. PushOutputNode(NewEl);
  1913. Try
  1914. ConvertBaseShortList(AElement, El, True)
  1915. Finally
  1916. PopOutputNode;
  1917. end;
  1918. end
  1919. else
  1920. AppendText(NewEl,El['id']);
  1921. l:=El['id'];
  1922. DescrEl := Engine.FindShortDescr(AElement.GetModule,L);
  1923. if Assigned(DescrEl) then
  1924. begin
  1925. AppendNbSp(CreatePara(CreateTD(TREl)), 2);
  1926. ParaEl := CreatePara(CreateTD(TREl));
  1927. ParaEl['class'] := 'cmt';
  1928. PushOutputNode(ParaEl);
  1929. try
  1930. ConvertShort(AElement, DescrEl);
  1931. finally
  1932. PopOutputNode;
  1933. end;
  1934. end;
  1935. end; // Link node
  1936. Node := Node.NextSibling;
  1937. end; // While
  1938. end;
  1939. Procedure THTMLWriter.AppendExampleSection(AElement : TPasElement;DocNode : TDocNode);
  1940. var
  1941. Node: TDOMNode;
  1942. // TableEl, El, TREl, TDEl, ParaEl, NewEl, DescrEl: TDOMElement;
  1943. fn,s: String;
  1944. f: Text;
  1945. begin
  1946. if not (Assigned(DocNode) and Assigned(DocNode.FirstExample)) then
  1947. Exit;
  1948. Node := DocNode.FirstExample;
  1949. while Assigned(Node) do
  1950. begin
  1951. if (Node.NodeType = ELEMENT_NODE) and (Node.NodeName = 'example') then
  1952. begin
  1953. fn:=Engine.GetExampleFilename(TDOMElement(Node));
  1954. If (fn<>'') then
  1955. begin
  1956. AppendText(CreateH2(BodyElement), SDocExample);
  1957. try
  1958. Assign(f, FN);
  1959. Reset(f);
  1960. try
  1961. PushOutputNode(BodyElement);
  1962. DescrBeginCode(False, TDOMElement(Node)['highlighter']);
  1963. while not EOF(f) do
  1964. begin
  1965. ReadLn(f, s);
  1966. DescrWriteCodeLine(s);
  1967. end;
  1968. DescrEndCode;
  1969. PopOutputNode;
  1970. finally
  1971. Close(f);
  1972. end;
  1973. except
  1974. on e: Exception do
  1975. begin
  1976. e.Message := '[example] ' + e.Message;
  1977. raise;
  1978. end;
  1979. end;
  1980. end;
  1981. end;
  1982. Node := Node.NextSibling;
  1983. end;
  1984. end;
  1985. procedure THTMLWriter.AppendFooter;
  1986. Var
  1987. S : String;
  1988. F : TDomElement;
  1989. begin
  1990. if FooterFile<>'' then
  1991. ReadXMLFragment(BodyElement, FooterFile)
  1992. else if IncludeDateInFooter then
  1993. begin
  1994. CreateEl(BodyElement, 'hr');
  1995. F:=CreateEl(BodyElement,'span');
  1996. F['class']:='footer';
  1997. If (FDateFormat='') then
  1998. S:=DateToStr(Date)
  1999. else
  2000. S:=FormatDateTime(FDateFormat,Date);
  2001. AppendText(F,Format(SDocDateGenerated,[S]));
  2002. end;
  2003. end;
  2004. procedure THTMLWriter.FinishElementPage(AElement: TPasElement);
  2005. var
  2006. DocNode: TDocNode;
  2007. begin
  2008. DocNode := Engine.FindDocNode(AElement);
  2009. If Assigned(DocNode) then
  2010. begin
  2011. // Description
  2012. if Assigned(DocNode.Descr) then
  2013. AppendDescrSection(AElement, BodyElement, DocNode.Descr, SDocDescription);
  2014. // Append "Errors" section
  2015. if Assigned(DocNode.ErrorsDoc) then
  2016. AppendDescrSection(AElement, BodyElement, DocNode.ErrorsDoc, SDocErrors);
  2017. // Append Version info
  2018. if Assigned(DocNode.Version) then
  2019. AppendDescrSection(AElement, BodyElement, DocNode.Version, SDocVersion);
  2020. // Append "See also" section
  2021. AppendSeeAlsoSection(AElement,DocNode);
  2022. // Append examples, if present
  2023. AppendExampleSection(AElement,DocNode);
  2024. // Append notes, if present
  2025. ConvertNotes(AElement,DocNode.Notes);
  2026. end;
  2027. end;
  2028. Procedure THTMLWriter.CreateTopicPageBody(AElement : TTopicElement);
  2029. var
  2030. DocNode: TDocNode;
  2031. TableEl, TREl: TDOMElement;
  2032. I : Integer;
  2033. S : String;
  2034. begin
  2035. AppendTopicMenuBar(AElement);
  2036. DocNode:=AElement.TopicNode;
  2037. if Assigned(DocNode) then // should always be true, but we're being careful.
  2038. begin
  2039. AppendShortDescr(AElement,TitleElement, DocNode);
  2040. AppendShortDescr(AElement,CreateH2(BodyElement), DocNode);
  2041. if Assigned(DocNode.Descr) then
  2042. AppendDescrSection(AElement, BodyElement, DocNode.Descr, '');
  2043. AppendSeeAlsoSection(AElement,DocNode);
  2044. CreateTopicLinks(DocNode,AElement);
  2045. AppendExampleSection(AElement,DocNode);
  2046. ConvertNotes(AElement,DocNode.Notes);
  2047. end;
  2048. end;
  2049. procedure THTMLWriter.CreateClassHierarchyPage(AList : TStringList; AddUnit : Boolean);
  2050. Procedure PushClassElement;
  2051. Var
  2052. H : THTMLElement;
  2053. begin
  2054. H:=CreateEl(CurOutputNode, 'li');
  2055. H['class']:='classtree';
  2056. PushOutputNode(H);
  2057. H:=CreateEl(CurOutputNode, 'span');
  2058. H['class']:='toggletreeclose';
  2059. H['onclick']:='expandorcollapse(this)';
  2060. PushOutputNode(h);
  2061. AppendNbSp(h,1);
  2062. PopOutputNode;
  2063. end;
  2064. Procedure PushClassList;
  2065. Var
  2066. H : THTMLElement;
  2067. begin
  2068. H:=CreateEl(CurOutputNode, 'ul');
  2069. H['class']:='classtreelist';
  2070. PushOutputNode(h);
  2071. end;
  2072. Procedure AppendClass(E : TDomElement);
  2073. Var
  2074. N : TDomNode;
  2075. P,PM : TPasElement;
  2076. NN : String;
  2077. EN : String;
  2078. LL : TstringList;
  2079. I,J : Integer;
  2080. begin
  2081. EN:=Package.Name+'.'+E['unit']+'.'+E.NodeName;
  2082. J:=AList.IndexOf(EN);
  2083. If J<>-1 then
  2084. P:=AList.Objects[J] as TPasElement
  2085. else
  2086. P:=Engine.FindElement(EN);
  2087. PushClassElement;
  2088. try
  2089. if (P<>Nil) then
  2090. begin
  2091. AppendHyperLink(CurOutputNode,P);
  2092. PM:=P.Getmodule;
  2093. if (PM<>Nil) then
  2094. begin
  2095. AppendText(CurOutputNode,' (');
  2096. AppendHyperLink(CurOutputNode,PM);
  2097. AppendText(CurOutputNode,')');
  2098. end
  2099. end
  2100. else
  2101. AppendText(CurOutputNode,E.Nodename);
  2102. LL:=TStringList.Create;
  2103. try
  2104. N:=E.FirstChild;
  2105. While (N<>Nil) do
  2106. begin
  2107. if (N.NodeType=ELEMENT_NODE) then
  2108. LL.AddObject(N.NodeName,N);
  2109. N:=N.NextSibling;
  2110. end;
  2111. if (LL.Count>0) then
  2112. begin
  2113. LL.Sorted:=true;
  2114. PushClassList;
  2115. try
  2116. For I:=0 to LL.Count-1 do
  2117. AppendClass(LL.Objects[i] as TDomElement);
  2118. finally
  2119. PopOutputNode;
  2120. end;
  2121. end;
  2122. finally
  2123. LL.Free;
  2124. end;
  2125. Finally
  2126. PopOutputNode;
  2127. end;
  2128. end;
  2129. Var
  2130. B : TClassTreeBuilder;
  2131. E : TDomElement;
  2132. F : TFileStream;
  2133. begin
  2134. PushOutputNode(BodyElement);
  2135. try
  2136. B:=TClassTreeBuilder.Create(Package,okClass);
  2137. try
  2138. B.BuildTree(AList);
  2139. // Classes
  2140. WriteXMLFile(B.ClassTree,'tree.xml');
  2141. // Dummy TObject
  2142. E:=B.ClassTree.DocumentElement;
  2143. PushClassList;
  2144. try
  2145. AppendClass(E);
  2146. finally
  2147. PopOutputNode;
  2148. end;
  2149. finally
  2150. B.Free;
  2151. end;
  2152. finally
  2153. PopOutputNode;
  2154. end;
  2155. end;
  2156. procedure THTMLWriter.CreatePackageClassHierarchy;
  2157. Const
  2158. SFunc = 'function expandorcollapse (o) {'+sLineBreak+
  2159. ' o.className = (o.className=="toggletreeclose") ? "toggletreeopen" : "toggletreeclose";'+sLineBreak+
  2160. ' o.parentNode.className = (o.className=="toggletreeclose") ? "classtree" : "classtreeclosed";'+sLineBreak+
  2161. ' return false;'+sLineBreak+
  2162. '}';
  2163. Var
  2164. L : TStringList;
  2165. I : Integer;
  2166. M : TPasModule;
  2167. E : TPasElement;
  2168. S : String;
  2169. SE : THTMLElement;
  2170. begin
  2171. SE := Doc.CreateElement('script');
  2172. AppendText(SE,SFunc);
  2173. HeadElement.AppendChild(SE);
  2174. L:=TStringList.Create;
  2175. try
  2176. L.Capacity:=PageInfos.Count; // Too much, but that doesn't hurt.
  2177. For I:=0 to Package.Modules.Count-1 do
  2178. begin
  2179. M:=TPasModule(Package.Modules[i]);
  2180. if Not (M is TPasExternalModule) then
  2181. Self.AddElementsFromList(L,M.InterfaceSection.Classes,True)
  2182. end;
  2183. AppendMenuBar(ClassHierarchySubIndex);
  2184. S:=Package.Name;
  2185. If Length(S)>0 then
  2186. Delete(S,1,1);
  2187. AppendTitle(Format(SDocPackageClassHierarchy, [S]));
  2188. CreateClassHierarchyPage(L,True);
  2189. Finally
  2190. L.Free;
  2191. end;
  2192. end;
  2193. procedure THTMLWriter.CreatePageBody(AElement: TPasElement;
  2194. ASubpageIndex: Integer);
  2195. var
  2196. i: Integer;
  2197. Element: TPasElement;
  2198. begin
  2199. CurDirectory := Allocator.GetFilename(AElement, ASubpageIndex);
  2200. i := Length(CurDirectory);
  2201. while (i > 0) and not (CurDirectory[i] in AllowDirectorySeparators) do
  2202. Dec(i);
  2203. CurDirectory := Copy(CurDirectory, 1, i);
  2204. BaseDirectory := Allocator.GetRelativePathToTop(AElement);
  2205. if AElement.ClassType = TPasPackage then
  2206. begin
  2207. Module:=Nil;
  2208. If (ASubPageIndex=0) then
  2209. CreatePackagePageBody
  2210. else if ASubPageIndex=IndexSubIndex then
  2211. CreatePackageIndex
  2212. else if ASubPageIndex=ClassHierarchySubIndex then
  2213. CreatePackageClassHierarchy
  2214. end
  2215. else
  2216. begin
  2217. Element := AElement;
  2218. while (Element<>Nil) and (Element.ClassType<>TPasModule) do
  2219. Element := Element.Parent;
  2220. Module := TPasModule(Element);
  2221. if AElement.ClassType = TPasModule then
  2222. CreateModulePageBody(TPasModule(AElement), ASubpageIndex)
  2223. else if AElement.Parent.InheritsFrom(TPasClassType) then
  2224. CreateClassMemberPageBody(AElement)
  2225. else if AElement.ClassType = TPasConst then
  2226. CreateConstPageBody(TPasConst(AElement))
  2227. else if AElement.InheritsFrom(TPasClassType) then
  2228. CreateClassPageBody(TPasClassType(AElement), ASubpageIndex)
  2229. else if AElement.InheritsFrom(TPasType) then
  2230. CreateTypePageBody(TPasType(AElement))
  2231. else if AElement.ClassType = TPasVariable then
  2232. CreateVarPageBody(TPasVariable(AElement))
  2233. else if AElement.InheritsFrom(TPasProcedureBase) then
  2234. CreateProcPageBody(TPasProcedure(AElement))
  2235. else if AElement.ClassType = TTopicELement then
  2236. CreateTopicPageBody(TTopicElement(AElement))
  2237. end;
  2238. end;
  2239. procedure THTMLWriter.CreateIndexPage(L : TStringList);
  2240. Var
  2241. Lists : Array['A'..'Z'] of TStringList;
  2242. LOther : TStringList;
  2243. CL : TStringList;
  2244. TableEl, TREl, EL: TDOMElement;
  2245. E : TPasElement;
  2246. I,Rows,J,Index : Integer;
  2247. S : String;
  2248. C : Char;
  2249. begin
  2250. For C:='A' to 'Z' do
  2251. Lists[C]:=Nil;
  2252. L.Sort;
  2253. Cl:=Nil;
  2254. // Divide over alphabet
  2255. For I:=0 to L.Count-1 do
  2256. begin
  2257. S:=L[i];
  2258. E:=TPasElement(L.Objects[i]);
  2259. If not (E is TPasUnresolvedTypeRef) then
  2260. begin
  2261. If (S<>'') then
  2262. begin
  2263. C:=Upcase(S[1]);
  2264. If C='_' then
  2265. C:='A';
  2266. If (C in ['A'..'Z']) and (Lists[C]=Nil) then
  2267. begin
  2268. CL:=TStringList.Create;
  2269. Lists[C]:=CL;
  2270. end;
  2271. end;
  2272. if assigned(cl) then
  2273. CL.AddObject(S,E);
  2274. end;
  2275. end;
  2276. Try
  2277. // Create a quick jump table to all available letters.
  2278. TableEl := CreateTable(BodyElement);
  2279. TableEl['border']:='1';
  2280. TableEl['width']:='50%';
  2281. TREl := CreateTR(TableEl);
  2282. for C:='A' to 'Z' do
  2283. If (Lists[C]<>Nil) then
  2284. begin
  2285. El:=CreateTD_vtop(TREl);
  2286. AppendText(CreateLink(El,'#SECTION'+C),C);
  2287. If C<>'Z' then
  2288. AppendNBsp(El,1);
  2289. end;
  2290. // Now emit all identifiers.
  2291. TableEl:=Nil;
  2292. For C:='A' to 'Z' do
  2293. begin
  2294. CL:=Lists[C];
  2295. If CL<>Nil then
  2296. begin
  2297. El:=CreateH2(BodyElement);
  2298. AppendText(El,C);
  2299. CreateAnchor(El,'SECTION'+C);
  2300. TableEl := CreateTable(BodyElement);
  2301. TableEl['Width']:='80%';
  2302. // Determine number of rows needed
  2303. Rows:=(CL.Count div IndexColCount);
  2304. If ((CL.Count Mod IndexColCount)<>0) then
  2305. Inc(Rows);
  2306. // Fill rows
  2307. For I:=0 to Rows-1 do
  2308. begin
  2309. TREl := CreateTR(TableEl);
  2310. For J:=0 to IndexColCount-1 do
  2311. begin
  2312. El:=CreateTD_vtop(TREl);
  2313. Index:=(J*Rows)+I;
  2314. If (Index<CL.Count) then
  2315. begin
  2316. S:=CL[Index];
  2317. E:=TPasElement(CL.Objects[Index]);
  2318. AppendHyperlink(El,E);
  2319. end;
  2320. end;
  2321. end;
  2322. end; // have List
  2323. end; // For C:=
  2324. Finally
  2325. for C:='A' to 'Z' do
  2326. FreeAndNil(Lists[C]);
  2327. end;
  2328. end;
  2329. Procedure THTMLWriter.AddElementsFromList(L : TStrings; List : TFPList; UsePathName : Boolean = False);
  2330. Var
  2331. I : Integer;
  2332. El : TPasElement;
  2333. begin
  2334. For I:=0 to List.Count-1 do
  2335. begin
  2336. El:=TPasElement(List[I]);
  2337. if UsePathName then
  2338. L.AddObject(El.PathName,El)
  2339. else
  2340. L.AddObject(El.Name,El);
  2341. If el is TPasEnumType then
  2342. AddElementsFromList(L,TPasEnumType(el).Values);
  2343. end;
  2344. end;
  2345. procedure THTMLWriter.AddModuleIdentifiers(AModule : TPasModule; L : TStrings);
  2346. begin
  2347. AddElementsFromList(L,AModule.InterfaceSection.Consts);
  2348. AddElementsFromList(L,AModule.InterfaceSection.Types);
  2349. AddElementsFromList(L,AModule.InterfaceSection.Functions);
  2350. AddElementsFromList(L,AModule.InterfaceSection.Classes);
  2351. AddElementsFromList(L,AModule.InterfaceSection.Variables);
  2352. AddElementsFromList(L,AModule.InterfaceSection.ResStrings);
  2353. end;
  2354. procedure THTMLWriter.CreatePackageIndex;
  2355. Var
  2356. L : TStringList;
  2357. I : Integer;
  2358. M : TPasModule;
  2359. E : TPasElement;
  2360. S : String;
  2361. begin
  2362. L:=TStringList.Create;
  2363. try
  2364. L.Capacity:=PageInfos.Count; // Too much, but that doesn't hurt.
  2365. For I:=0 to Package.Modules.Count-1 do
  2366. begin
  2367. M:=TPasModule(Package.Modules[i]);
  2368. L.AddObject(M.Name,M);
  2369. AddModuleIdentifiers(M,L);
  2370. end;
  2371. AppendMenuBar(IndexSubIndex);
  2372. S:=Package.Name;
  2373. If Length(S)>0 then
  2374. Delete(S,1,1);
  2375. AppendTitle(Format(SDocPackageIndex, [S]));
  2376. CreateIndexPage(L);
  2377. Finally
  2378. L.Free;
  2379. end;
  2380. end;
  2381. procedure THTMLWriter.CreatePackagePageBody;
  2382. var
  2383. DocNode: TDocNode;
  2384. TableEl, TREl: TDOMElement;
  2385. i: Integer;
  2386. ThisModule: TPasModule;
  2387. L : TStringList;
  2388. begin
  2389. AppendMenuBar(0);
  2390. AppendTitle(Format(SDocPackageTitle, [Copy(Package.Name, 2, 256)]));
  2391. AppendShortDescr(CreatePara(BodyElement), Package);
  2392. AppendText(CreateH2(BodyElement), SDocUnits);
  2393. TableEl := CreateTable(BodyElement);
  2394. L:=TStringList.Create;
  2395. Try
  2396. L.Sorted:=True;
  2397. // Sort modules.
  2398. For I:=0 to Package.Modules.Count-1 do
  2399. L.AddObject(TPasModule(Package.Modules[i]).Name,TPasModule(Package.Modules[i]));
  2400. // Now create table.
  2401. for i:=0 to L.Count - 1 do
  2402. begin
  2403. ThisModule := TPasModule(L.Objects[i]);
  2404. TREl := CreateTR(TableEl);
  2405. AppendHyperlink(CreateCode(CreatePara(CreateTD_vtop(TREl))), ThisModule);
  2406. AppendShortDescrCell(TREl, ThisModule);
  2407. end;
  2408. Finally
  2409. L.Free;
  2410. end;
  2411. DocNode := Engine.FindDocNode(Package);
  2412. if Assigned(DocNode) then
  2413. begin
  2414. if Assigned(DocNode.Descr) then
  2415. AppendDescrSection(nil, BodyElement, DocNode.Descr, SDocDescription);
  2416. CreateTopicLinks(DocNode,Package);
  2417. end;
  2418. end;
  2419. Procedure THTMLWriter.CreateTopicLinks(Node : TDocNode; PasElement : TPasElement);
  2420. var
  2421. DocNode: TDocNode;
  2422. TableEl, TREl: TDOMElement;
  2423. First : Boolean;
  2424. ThisTopic: TPasElement;
  2425. begin
  2426. DocNode:=Node.FirstChild;
  2427. First:=True;
  2428. While Assigned(DocNode) do
  2429. begin
  2430. If DocNode.TopicNode then
  2431. begin
  2432. if first then
  2433. begin
  2434. First:=False;
  2435. AppendText(CreateH2(BodyElement), SDocRelatedTopics);
  2436. TableEl := CreateTable(BodyElement);
  2437. end;
  2438. TREl := CreateTR(TableEl);
  2439. ThisTopic:=FindTopicElement(DocNode);
  2440. if Assigned(ThisTopic) then
  2441. AppendHyperlink(CreateCode(CreatePara(CreateTD_vtop(TREl))), ThisTopic);
  2442. AppendShortDescrCell(TREl, ThisTopic);
  2443. end;
  2444. DocNode:=DocNode.NextSibling;
  2445. end;
  2446. end;
  2447. procedure THTMLWriter.CreateModuleIndexPage(AModule: TPasModule);
  2448. Var
  2449. L : TStringList;
  2450. begin
  2451. L:=TStringList.Create;
  2452. try
  2453. AddModuleIdentifiers(AModule,L);
  2454. AppendMenuBar(IndexSubIndex);
  2455. AppendTitle(Format(SDocModuleIndex, [AModule.Name]));
  2456. CreateIndexPage(L);
  2457. Finally
  2458. L.Free;
  2459. end;
  2460. end;
  2461. procedure THTMLWriter.CreateModulePageBody(AModule: TPasModule;
  2462. ASubpageIndex: Integer);
  2463. procedure CreateMainPage;
  2464. var
  2465. TableEl, TREl, TDEl, CodeEl: TDOMElement;
  2466. i: Integer;
  2467. UnitRef: TPasType;
  2468. DocNode: TDocNode;
  2469. begin
  2470. AppendMenuBar(0);
  2471. AppendTitle(Format(SDocUnitTitle, [AModule.Name]));
  2472. AppendShortDescr(CreatePara(BodyElement), AModule);
  2473. if AModule.InterfaceSection.UsesList.Count > 0 then
  2474. begin
  2475. TableEl := CreateTable(BodyElement);
  2476. AppendKw(CreateCode(CreatePara(CreateTD(CreateTR(TableEl)))), 'uses');
  2477. for i := 0 to AModule.InterfaceSection.UsesList.Count - 1 do
  2478. begin
  2479. UnitRef := TPasType(AModule.InterfaceSection.UsesList[i]);
  2480. DocNode := Engine.FindDocNode(UnitRef);
  2481. if Assigned(DocNode) and DocNode.IsSkipped then
  2482. continue;
  2483. TREl := CreateTR(TableEl);
  2484. TDEl := CreateTD_vtop(TREl);
  2485. CodeEl := CreateCode(CreatePara(TDEl));
  2486. AppendNbSp(CodeEl, 2);
  2487. AppendHyperlink(CodeEl, UnitRef);
  2488. if i < AModule.InterfaceSection.UsesList.Count - 1 then
  2489. AppendSym(CodeEl, ',')
  2490. else
  2491. AppendSym(CodeEl, ';');
  2492. AppendText(CodeEl, ' '); // Space for descriptions
  2493. AppendShortDescrCell(TREl, UnitRef);
  2494. end;
  2495. end;
  2496. DocNode := Engine.FindDocNode(AModule);
  2497. if Assigned(DocNode) then
  2498. begin
  2499. if Assigned(DocNode.Descr) then
  2500. AppendDescrSection(AModule, BodyElement, DocNode.Descr, SDocOverview);
  2501. ConvertNotes(AModule,DocNode.Notes);
  2502. CreateTopicLinks(DocNode,AModule);
  2503. end;
  2504. end;
  2505. procedure CreateSimpleSubpage(const ATitle: DOMString; AList: TFPList);
  2506. var
  2507. TableEl, TREl, TDEl, CodeEl: TDOMElement;
  2508. i, j: Integer;
  2509. Decl: TPasElement;
  2510. SortedList: TFPList;
  2511. DocNode: TDocNode;
  2512. S : String;
  2513. begin
  2514. AppendMenuBar(ASubpageIndex);
  2515. S:=ATitle;
  2516. AppendTitle(Format(SDocUnitTitle + ': %s', [AModule.Name, S]));
  2517. SortedList := TFPList.Create;
  2518. try
  2519. for i := 0 to AList.Count - 1 do
  2520. begin
  2521. Decl := TPasElement(AList[i]);
  2522. DocNode := Engine.FindDocNode(Decl);
  2523. if (not Assigned(DocNode)) or (not DocNode.IsSkipped) then
  2524. begin
  2525. j := 0;
  2526. while (j < SortedList.Count) and (CompareText(
  2527. TPasElement(SortedList[j]).PathName, Decl.PathName) < 0) do
  2528. Inc(j);
  2529. SortedList.Insert(j, Decl);
  2530. end;
  2531. end;
  2532. TableEl := CreateTable(BodyElement);
  2533. for i := 0 to SortedList.Count - 1 do
  2534. begin
  2535. Decl := TPasElement(SortedList[i]);
  2536. TREl := CreateTR(TableEl);
  2537. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  2538. AppendHyperlink(CodeEl, Decl);
  2539. AppendShortDescrCell(TREl, Decl);
  2540. end;
  2541. finally
  2542. SortedList.Free;
  2543. end;
  2544. end;
  2545. procedure CreateResStringsPage;
  2546. var
  2547. ParaEl: TDOMElement;
  2548. i, j: Integer;
  2549. Decl: TPasResString;
  2550. DocNode: TDocNode;
  2551. begin
  2552. AppendMenuBar(ResstrSubindex);
  2553. AppendTitle(Format(SDocUnitTitle + ': %s', [AModule.Name, SDocResStrings]));
  2554. for i := 0 to AModule.InterfaceSection.ResStrings.Count - 1 do
  2555. begin
  2556. Decl := TPasResString(AModule.InterfaceSection.ResStrings[i]);
  2557. CreateEl(BodyElement, 'a')['name'] := LowerCase(Decl.Name);
  2558. ParaEl := CreatePara(BodyElement);
  2559. AppendText(CreateCode(ParaEl), Decl.Name);
  2560. CreateEl(ParaEl, 'br');
  2561. AppendText(ParaEl, Decl.Expr.getDeclaration(true));
  2562. end;
  2563. end;
  2564. begin
  2565. case ASubpageIndex of
  2566. 0:
  2567. CreateMainPage;
  2568. ResstrSubindex:
  2569. CreateResStringsPage;
  2570. ConstsSubindex:
  2571. CreateSimpleSubpage(SDocConstants, AModule.InterfaceSection.Consts);
  2572. TypesSubindex:
  2573. CreateSimpleSubpage(SDocTypes, AModule.InterfaceSection.Types);
  2574. ClassesSubindex:
  2575. CreateSimpleSubpage(SDocClasses, AModule.InterfaceSection.Classes);
  2576. ProcsSubindex:
  2577. CreateSimpleSubpage(SDocProceduresAndFunctions, AModule.InterfaceSection.Functions);
  2578. VarsSubindex:
  2579. CreateSimpleSubpage(SDocVariables, AModule.InterfaceSection.Variables);
  2580. IndexSubIndex:
  2581. CreateModuleIndexPage(AModule);
  2582. end;
  2583. end;
  2584. procedure THTMLWriter.CreateConstPageBody(AConst: TPasConst);
  2585. var
  2586. TableEl, CodeEl: TDOMElement;
  2587. begin
  2588. AppendMenuBar(-1);
  2589. AppendTitle(AConst.Name);
  2590. AppendShortDescr(CreatePara(BodyElement), AConst);
  2591. AppendText(CreateH2(BodyElement), SDocDeclaration);
  2592. AppendSourceRef(AConst);
  2593. TableEl := CreateTable(BodyElement);
  2594. CodeEl := CreateCode(CreatePara(CreateTD(CreateTR(TableEl))));
  2595. AppendKw(CodeEl, 'const');
  2596. AppendText(CodeEl, ' ' + AConst.Name);
  2597. if Assigned(AConst.VarType) then
  2598. begin
  2599. AppendSym(CodeEl, ': ');
  2600. AppendType(CodeEl, TableEl, AConst.VarType, False);
  2601. end;
  2602. AppendPasSHFragment(CodeEl, ' = ' + AConst.Expr.GetDeclaration(True) + ';', 0);
  2603. FinishElementPage(AConst);
  2604. end;
  2605. procedure THTMLWriter.AppendTypeDecl(AType: TPasType; TableEl,CodeEl : TDomElement);
  2606. Var
  2607. TREl : TDomElement;
  2608. i: Integer;
  2609. s: String;
  2610. EnumType: TPasEnumType;
  2611. EnumValue: TPasEnumValue;
  2612. Variable: TPasVariable;
  2613. begin
  2614. // Alias
  2615. if AType.ClassType = TPasAliasType then
  2616. begin
  2617. if Assigned(TPasAliasType(AType).DestType) then
  2618. AppendHyperlink(CodeEl, TPasAliasType(AType).DestType)
  2619. else
  2620. AppendText(CreateWarning(CodeEl), '<Destination type is NIL>');
  2621. AppendSym(CodeEl, ';');
  2622. end else
  2623. // Class of
  2624. if AType.ClassType = TPasClassOfType then
  2625. begin
  2626. AppendKw(CodeEl, 'class of ');
  2627. AppendHyperlink(CodeEl, TPasClassOfType(AType).DestType);
  2628. AppendSym(CodeEl, ';');
  2629. end else
  2630. // Enumeration
  2631. if AType.ClassType = TPasEnumType then
  2632. begin
  2633. AppendSym(CodeEl, '(');
  2634. for i := 0 to TPasEnumType(AType).Values.Count - 1 do
  2635. begin
  2636. EnumValue := TPasEnumValue(TPasEnumType(AType).Values[i]);
  2637. TREl := CreateTR(TableEl);
  2638. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  2639. AppendShortDescrCell(TREl, EnumValue);
  2640. AppendNbSp(CodeEl, 2);
  2641. s := EnumValue.Name;
  2642. if EnumValue.AssignedValue<>'' then
  2643. s := s + ' = ' + EnumValue.AssignedValue;
  2644. if i < TPasEnumType(AType).Values.Count - 1 then
  2645. s := s + ',';
  2646. AppendPasSHFragment(CodeEl, s, 0);
  2647. end;
  2648. AppendSym(CreateCode(CreatePara(CreateTD(CreateTR(TableEl)))), ');');
  2649. end else
  2650. // Pointer type
  2651. if AType.ClassType = TPasPointerType then
  2652. begin
  2653. AppendSym(CodeEl, '^');
  2654. if Assigned(TPasPointerType(AType).DestType) then
  2655. AppendHyperlink(CodeEl, TPasPointerType(AType).DestType)
  2656. else
  2657. AppendText(CreateWarning(CodeEl), '<Destination type is NIL>');
  2658. AppendSym(CodeEl, ';');
  2659. end else
  2660. if AType.InheritsFrom(TPasProcedureType) then
  2661. begin
  2662. AppendSym(AppendType(CodeEl, TableEl, TPasType(AType), True), ';');
  2663. AppendProcArgsSection(BodyElement, TPasProcedureType(AType));
  2664. end else
  2665. // Record
  2666. if AType.ClassType = TPasRecordType then
  2667. begin
  2668. CodeEl := AppendRecordType(CodeEl, TableEl, TPasRecordType(AType), 0);
  2669. AppendSym(CodeEl, ';');
  2670. end else
  2671. // Set
  2672. if AType.ClassType = TPasSetType then
  2673. begin
  2674. AppendKw(CodeEl, 'set of ');
  2675. if TPasSetType(AType).EnumType.ClassType = TPasEnumType then
  2676. begin
  2677. AppendSym(CodeEl, '(');
  2678. EnumType := TPasEnumType(TPasSetType(AType).EnumType);
  2679. for i := 0 to EnumType.Values.Count - 1 do
  2680. begin
  2681. EnumValue := TPasEnumValue(EnumType.Values[i]);
  2682. TREl := CreateTR(TableEl);
  2683. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  2684. AppendShortDescrCell(TREl, EnumValue);
  2685. AppendNbSp(CodeEl, 2);
  2686. s := EnumValue.Name;
  2687. if (EnumValue.AssignedValue<>'') then
  2688. s := s + ' = ' + EnumValue.AssignedValue;
  2689. if i < EnumType.Values.Count - 1 then
  2690. s := s + ',';
  2691. AppendPasSHFragment(CodeEl, s, 0);
  2692. end;
  2693. AppendSym(CreateCode(CreatePara(CreateTD(CreateTR(TableEl)))), ');');
  2694. end else
  2695. begin
  2696. AppendHyperlink(CodeEl, TPasSetType(AType).EnumType);
  2697. AppendSym(CodeEl, ';');
  2698. end;
  2699. end else
  2700. // Type alias
  2701. if AType.ClassType = TPasTypeAliasType then
  2702. begin
  2703. AppendKw(CodeEl, 'type ');
  2704. AppendHyperlink(CodeEl, TPasTypeAliasType(AType).DestType);
  2705. AppendSym(CodeEl, ';');
  2706. end else
  2707. // Probably one of the simple types, which allowed in other places as wel...
  2708. AppendSym(AppendType(CodeEl, TableEl, TPasType(AType), True), ';');
  2709. end;
  2710. procedure THTMLWriter.CreateTypePageBody(AType: TPasType);
  2711. var
  2712. TableEl, TREl, TDEl, CodeEl: TDOMElement;
  2713. DocNode: TDocNode;
  2714. i: Integer;
  2715. s: String;
  2716. EnumType: TPasEnumType;
  2717. EnumValue: TPasEnumValue;
  2718. Variable: TPasVariable;
  2719. begin
  2720. AppendMenuBar(-1);
  2721. AppendTitle(AType.Name);
  2722. AppendShortDescr(CreatePara(BodyElement), AType);
  2723. AppendText(CreateH2(BodyElement), SDocDeclaration);
  2724. AppendSourceRef(AType);
  2725. TableEl := CreateTable(BodyElement);
  2726. TREl := CreateTR(TableEl);
  2727. TDEl := CreateTD(TREl);
  2728. CodeEl := CreateCode(CreatePara(TDEl));
  2729. DocNode := Engine.FindDocNode(AType);
  2730. AppendKw(CodeEl, 'type ');
  2731. AppendText(CodeEl, AType.Name);
  2732. AppendSym(CodeEl, ' = ');
  2733. If Assigned(DocNode) and
  2734. Assigned(DocNode.Node) and
  2735. (Docnode.Node['opaque']='1') then
  2736. AppendText(CodeEl,SDocOpaque)
  2737. else
  2738. begin
  2739. AppendTypeDecl(AType,TableEl,CodeEl);
  2740. end;
  2741. FinishElementPage(AType);
  2742. end;
  2743. function PropertyFilter(AMember: TPasElement): Boolean;
  2744. begin
  2745. Result := (AMember.ClassType = TPasProperty) and
  2746. (Copy(AMember.Name, 1, 2) <> 'On');
  2747. end;
  2748. function MethodFilter(AMember: TPasElement): Boolean;
  2749. begin
  2750. Result := AMember.InheritsFrom(TPasProcedureBase);
  2751. end;
  2752. function EventFilter(AMember: TPasElement): Boolean;
  2753. begin
  2754. Result := (AMember.ClassType = TPasProperty) and
  2755. (Copy(AMember.Name, 1, 2) = 'On');
  2756. end;
  2757. procedure THTMLWriter.CreateClassPageBody(AClass: TPasClassType;
  2758. ASubpageIndex: Integer);
  2759. type
  2760. TMemberFilter = function(AMember: TPasElement): Boolean;
  2761. var
  2762. ParaEl: TDOMElement;
  2763. procedure AppendMemberListLink(AListSubpageIndex: Integer;
  2764. const AText: DOMString);
  2765. var
  2766. LinkEl: TDOMElement;
  2767. begin
  2768. if FUseMenuBrackets then
  2769. AppendText(ParaEl, '[');
  2770. LinkEl := CreateEl(ParaEl, 'a');
  2771. LinkEl['href'] :=
  2772. FixHtmlPath(ResolveLinkWithinPackage(AClass, AListSubpageIndex));
  2773. LinkEl['onClick'] := 'window.open(''' + LinkEl['href'] + ''', ''list'', ' +
  2774. '''dependent=yes,resizable=yes,scrollbars=yes,height=400,width=300''); return false;';
  2775. AppendText(LinkEl, AText);
  2776. AppendText(ParaEl, ' (');
  2777. LinkEl := CreateEl(ParaEl, 'a');
  2778. LinkEl['href'] :=
  2779. FixHtmlPath(ResolveLinkWithinPackage(AClass, AListSubpageIndex + 1));
  2780. LinkEl['onClick'] := 'window.open(''' + LinkEl['href'] + ''', ''list'', ' +
  2781. '''dependent=yes,resizable=yes,scrollbars=yes,height=400,width=300''); return false;';
  2782. AppendText(LinkEl, SDocByName);
  2783. AppendText(ParaEl, ')');
  2784. if FUseMenuBrackets then
  2785. AppendText(ParaEl, '] ')
  2786. else
  2787. AppendText(ParaEl, ' ');
  2788. end;
  2789. procedure AppendGenericTypes(CodeEl : TDomElement; AList : TFPList; isSpecialize : Boolean);
  2790. Var
  2791. I : integer;
  2792. begin
  2793. for I:=0 to AList.Count-1 do
  2794. begin
  2795. if I=0 then
  2796. AppendSym(CodeEl, '<')
  2797. else
  2798. AppendSym(CodeEl, ',');
  2799. AppendText(CodeEl,TPasGenericTemplateType(AList[i]).Name);
  2800. end;
  2801. AppendSym(CodeEl, '>');
  2802. end;
  2803. procedure CreateMainPage;
  2804. var
  2805. TableEl, TREl, TDEl, CodeEl: TDOMElement;
  2806. DocNode: TDocNode;
  2807. Member: TPasElement;
  2808. MVisibility,
  2809. CurVisibility: TPasMemberVisibility;
  2810. i: Integer;
  2811. s: String;
  2812. t : TPasType;
  2813. ah,ol,wt,ct,wc,cc : boolean;
  2814. ThisInterface,
  2815. ThisClass: TPasClassType;
  2816. HaveSeenTObject: Boolean;
  2817. begin
  2818. AppendMenuBar(-1);
  2819. AppendTitle(AClass.Name);
  2820. ParaEl := CreatePara(BodyElement);
  2821. AppendMemberListLink(PropertiesByInheritanceSubindex, SDocProperties);
  2822. AppendMemberListLink(MethodsByInheritanceSubindex, SDocMethods);
  2823. AppendMemberListLink(EventsByInheritanceSubindex, SDocEvents);
  2824. AppendShortDescr(CreatePara(BodyElement), AClass);
  2825. AppendText(CreateH2(BodyElement), SDocDeclaration);
  2826. AppendSourceRef(AClass);
  2827. TableEl := CreateTable(BodyElement);
  2828. TREl := CreateTR(TableEl);
  2829. TDEl := CreateTD(TREl);
  2830. CodeEl := CreateCode(CreatePara(TDEl));
  2831. AppendKw(CodeEl, 'type');
  2832. if AClass.ObjKind=okGeneric then
  2833. AppendKw(CodeEl, ' generic ');
  2834. AppendText(CodeEl, ' ' + AClass.Name + ' ');
  2835. if AClass.ObjKind=okGeneric then
  2836. AppendGenericTypes(CodeEl,AClass.GenericTemplateTypes,false);
  2837. AppendSym(CodeEl, '=');
  2838. AppendText(CodeEl, ' ');
  2839. if AClass.ObjKind<>okSpecialize then
  2840. AppendKw(CodeEl, ObjKindNames[AClass.ObjKind])
  2841. else
  2842. AppendKw(CodeEl, ' specialize ');
  2843. if Assigned(AClass.AncestorType) then
  2844. begin
  2845. if AClass.ObjKind=okSpecialize then
  2846. begin
  2847. AppendHyperlink(CodeEl, AClass.AncestorType);
  2848. AppendGenericTypes(CodeEl,AClass.GenericTemplateTypes,true)
  2849. end
  2850. else
  2851. begin
  2852. AppendSym(CodeEl, '(');
  2853. AppendHyperlink(CodeEl, AClass.AncestorType);
  2854. if AClass.Interfaces.count>0 Then
  2855. begin
  2856. for i:=0 to AClass.interfaces.count-1 do
  2857. begin
  2858. AppendSym(CodeEl, ', ');
  2859. AppendHyperlink(CodeEl,TPasClassType(AClass.Interfaces[i]));
  2860. end;
  2861. end;
  2862. AppendSym(CodeEl, ')');
  2863. end;
  2864. end;
  2865. if AClass.Members.Count > 0 then
  2866. begin
  2867. wt:=False;
  2868. wc:=False;
  2869. CurVisibility := visDefault;
  2870. for i := 0 to AClass.Members.Count - 1 do
  2871. begin
  2872. Member := TPasElement(AClass.Members[i]);
  2873. MVisibility:=Member.Visibility;
  2874. ol:=(Member is TPasOverloadedProc);
  2875. ah:=ol or ((Member is TPasProcedure) and (TPasProcedure(Member).ProcType.Args.Count > 0));
  2876. if ol then
  2877. Member:=TPasElement((Member as TPasOverloadedProc).Overloads[0]);
  2878. if ((MVisibility = visPrivate) and Engine.HidePrivate) or
  2879. ( (MVisibility = visProtected) and Engine.HideProtected) then
  2880. continue;
  2881. if (CurVisibility <> MVisibility) then
  2882. begin
  2883. CurVisibility := MVisibility;
  2884. s:=VisibilityNames[MVisibility];
  2885. AppendKw(CreateCode(CreatePara(CreateTD(CreateTR(TableEl)))), s);
  2886. end;
  2887. ct:=(Member is TPasType);
  2888. if ct and (not wt) then
  2889. begin
  2890. AppendKw(CreateCode(CreatePara(CreateTD(CreateTR(TableEl)))), 'Type');
  2891. end;
  2892. wt:=ct;
  2893. cc:=(Member is TPasConst);
  2894. if cc and (not wc) then
  2895. begin
  2896. AppendKw(CreateCode(CreatePara(CreateTD(CreateTR(TableEl)))), 'Const');
  2897. end;
  2898. wc:=cc;
  2899. TREl := CreateTR(TableEl);
  2900. CodeEl := CreateCode(CreatePara(CreateTD_vtop(TREl)));
  2901. AppendNbSp(CodeEl, 2);
  2902. AppendShortDescrCell(TREl, Member);
  2903. if (Member is TPasProcedureBase) then
  2904. begin
  2905. AppendKw(CodeEl, TPasProcedureBase(Member).TypeName + ' ');
  2906. AppendHyperlink(CodeEl, Member);
  2907. if ah then
  2908. AppendSym(CodeEl, '();')
  2909. else
  2910. AppendSym(CodeEl, ';');
  2911. if Not OL then
  2912. AppendProcExt(CodeEl, TPasProcedure(Member));
  2913. end
  2914. else if (Member is TPasConst) then
  2915. begin
  2916. AppendHyperlink(CodeEl, Member);
  2917. If Assigned(TPasConst(Member).VarType) then
  2918. begin
  2919. AppendSym(CodeEl, ' = ');
  2920. AppendTypeDecl(TPasType(Member),TableEl,CodeEl);
  2921. end;
  2922. AppendSym(CodeEl, ' = ');
  2923. AppendText(CodeEl,TPasConst(Member).Expr.GetDeclaration(True));
  2924. end
  2925. else if (Member is TPasType) then
  2926. begin
  2927. AppendHyperlink(CodeEl, Member);
  2928. AppendSym(CodeEl, ' = ');
  2929. AppendTypeDecl(TPasType(Member),TableEl,CodeEl);
  2930. end
  2931. else if (Member is TPasProperty) then
  2932. begin
  2933. AppendKw(CodeEl, 'property ');
  2934. AppendHyperlink(CodeEl, Member);
  2935. t:=TPasProperty(Member).ResolvedType;
  2936. if Assigned(T) then
  2937. begin
  2938. AppendSym(CodeEl, ': ');
  2939. AppendHyperlink(CodeEl, T);
  2940. end;
  2941. AppendSym(CodeEl, ';');
  2942. if TPasProperty(Member).IsDefault then
  2943. begin
  2944. AppendKw(CodeEl, ' default');
  2945. AppendSym(CodeEl, ';');
  2946. end;
  2947. if (TPasProperty(Member).ImplementsName<>'') then
  2948. begin
  2949. AppendKw(CodeEl, ' implements');
  2950. AppendText(CodeEl, ' '+TPasProperty(Member).ImplementsName);
  2951. AppendSym(CodeEl, ';');
  2952. end;
  2953. SetLength(s, 0);
  2954. if Length(TPasProperty(Member).ReadAccessorName) > 0 then
  2955. s := s + 'r';
  2956. if Length(TPasProperty(Member).WriteAccessorName) > 0 then
  2957. s := s + 'w';
  2958. if Length(TPasProperty(Member).StoredAccessorName) > 0 then
  2959. s := s + 's';
  2960. if Length(s) > 0 then
  2961. AppendText(CodeEl, ' [' + s + ']');
  2962. end
  2963. else if (Member is TPasVariable) then
  2964. begin
  2965. AppendHyperlink(CodeEl, Member);
  2966. AppendSym(CodeEl, ': ');
  2967. AppendHyperlink(CodeEl, TPasVariable(Member).VarType);
  2968. AppendSym(CodeEl, ';');
  2969. end
  2970. else
  2971. AppendText(CreateWarning(CodeEl), '<' + Member.ClassName + '>');
  2972. end;
  2973. CodeEl := CreateCode(CreatePara(CreateTD(CreateTR(TableEl))));
  2974. end;
  2975. AppendText(CodeEl, ' '); // !!!: Dirty trick, necessary for current XML writer
  2976. if not AClass.IsShortDefinition then
  2977. AppendKw(CodeEl, 'end');
  2978. AppendSym(CodeEl, ';');
  2979. AppendText(CreateH2(BodyElement), SDocInheritance);
  2980. TableEl := CreateTable(BodyElement);
  2981. HaveSeenTObject := AClass.ObjKind <> okClass;
  2982. ThisClass := AClass;
  2983. while True do
  2984. begin
  2985. TREl := CreateTR(TableEl);
  2986. TDEl := CreateTD_vtop(TREl);
  2987. TDEl['align'] := 'center';
  2988. CodeEl := CreateCode(CreatePara(TDEl));
  2989. AppendHyperlink(CodeEl, ThisClass);
  2990. if ThisClass.Interfaces.count>0 then
  2991. begin
  2992. for i:=0 to ThisClass.interfaces.count-1 do
  2993. begin
  2994. ThisInterface:=TPasClassType(ThisClass.Interfaces[i]);
  2995. AppendText(CodeEl,',');
  2996. AppendHyperlink(CodeEl, ThisInterface);
  2997. end;
  2998. end;
  2999. AppendShortDescrCell(TREl, ThisClass);
  3000. if HaveSeenTObject or (CompareText(ThisClass.Name, 'TObject') = 0) then
  3001. HaveSeenTObject := True
  3002. else
  3003. begin
  3004. TDEl := CreateTD(CreateTR(TableEl));
  3005. TDEl['align'] := 'center';
  3006. AppendText(TDEl, '|');
  3007. end;
  3008. if Assigned(ThisClass.AncestorType) then
  3009. begin
  3010. if ThisClass.AncestorType.InheritsFrom(TPasClassType) then
  3011. ThisClass := TPasClassType(ThisClass.AncestorType)
  3012. else
  3013. begin
  3014. TDEl := CreateTD(CreateTR(TableEl));
  3015. TDEl['align'] := 'center';
  3016. AppendText(CreateCode(CreatePara(TDEl)), ThisClass.AncestorType.Name);
  3017. if CompareText(ThisClass.AncestorType.Name, 'TObject') = 0 then
  3018. HaveSeenTObject := True
  3019. else
  3020. begin
  3021. TDEl := CreateTD(CreateTR(TableEl));
  3022. TDEl['align'] := 'center';
  3023. AppendText(TDEl, '?');
  3024. end;
  3025. break;
  3026. end
  3027. end else
  3028. break;
  3029. end;
  3030. if not HaveSeenTObject then
  3031. begin
  3032. TDEl := CreateTD(CreateTR(TableEl));
  3033. TDEl['align'] := 'center';
  3034. AppendText(CreateCode(CreatePara(TDEl)), 'TObject');
  3035. end;
  3036. FinishElementPage(AClass);
  3037. end;
  3038. procedure CreateInheritanceSubpage(AFilter: TMemberFilter);
  3039. var
  3040. ThisClass: TPasClassType;
  3041. i: Integer;
  3042. Member: TPasElement;
  3043. TableEl, TREl, TDEl, ParaEl, LinkEl: TDOMElement;
  3044. begin
  3045. TableEl := CreateTable(BodyElement);
  3046. ThisClass := AClass;
  3047. while True do
  3048. begin
  3049. TREl := CreateTR(TableEl);
  3050. TDEl := CreateTD(TREl);
  3051. TDEl['colspan'] := '3';
  3052. CreateTD(TREl);
  3053. LinkEl := AppendHyperlink(CreateEl(CreateCode(CreatePara(TDEl)), 'b'), ThisClass);
  3054. if Assigned(LinkEl) then
  3055. LinkEl['onClick'] := 'opener.location.href = ''' + LinkEl['href'] +
  3056. '''; return false;';
  3057. for i := 0 to ThisClass.Members.Count - 1 do
  3058. begin
  3059. Member := TPasElement(ThisClass.Members[i]);
  3060. if ((Member.Visibility = visPrivate) and Engine.HidePrivate) or
  3061. ((Member.Visibility = visProtected) and Engine.HideProtected) or
  3062. not AFilter(Member) then
  3063. continue;
  3064. TREl := CreateTR(TableEl);
  3065. ParaEl := CreatePara(CreateTD(TREl));
  3066. case Member.Visibility of
  3067. visPrivate:
  3068. AppendText(ParaEl, 'pv');
  3069. visProtected:
  3070. AppendText(ParaEl, 'pt');
  3071. visPublished:
  3072. AppendText(ParaEl, 'pl');
  3073. end;
  3074. AppendNbSp(ParaEl, 1);
  3075. ParaEl := CreateTD(TREl);
  3076. if (Member.ClassType = TPasProperty) and
  3077. (Length(TPasProperty(Member).WriteAccessorName) = 0) then
  3078. begin
  3079. AppendText(ParaEl, 'ro');
  3080. AppendNbSp(ParaEl, 1);
  3081. end;
  3082. LinkEl := AppendHyperlink(CreatePara(CreateTD(TREl)), Member);
  3083. if Assigned(LinkEl) then
  3084. LinkEl['onClick'] := 'opener.location.href = ''' + LinkEl['href'] +
  3085. '''; return false;';
  3086. end;
  3087. if (not Assigned(ThisClass.AncestorType)) or
  3088. (not (ThisClass.AncestorType.ClassType = TPasClassType)) then
  3089. break;
  3090. ThisClass := TPasClassType(ThisClass.AncestorType);
  3091. AppendNbSp(CreatePara(CreateTD(CreateTR(TableEl))), 1);
  3092. end;
  3093. end;
  3094. procedure CreateSortedSubpage(AFilter: TMemberFilter);
  3095. var
  3096. List: TFPList;
  3097. ThisClass: TPasClassType;
  3098. i, j: Integer;
  3099. Member: TPasElement;
  3100. TableEl, TREl, TDEl, ParaEl, LinkEl: TDOMElement;
  3101. begin
  3102. List := TFPList.Create;
  3103. try
  3104. ThisClass := AClass;
  3105. while True do
  3106. begin
  3107. for i := 0 to ThisClass.Members.Count - 1 do
  3108. begin
  3109. Member := TPasElement(ThisClass.Members[i]);
  3110. if (not (((Member.Visibility = visPrivate) and Engine.HidePrivate) or
  3111. ((Member.Visibility = visProtected) and Engine.HideProtected))) and
  3112. AFilter(Member) then
  3113. begin
  3114. j := 0;
  3115. while (j < List.Count) and
  3116. (CompareText(TPasElement(List[j]).Name, Member.Name) < 0) do
  3117. Inc(j);
  3118. List.Insert(j, Member);
  3119. end;
  3120. end;
  3121. if (not Assigned(ThisClass.AncestorType)) or
  3122. (not (ThisClass.AncestorType.ClassType = TPasClassType)) then
  3123. break;
  3124. ThisClass := TPasClassType(ThisClass.AncestorType);
  3125. end;
  3126. TableEl := CreateTable(BodyElement);
  3127. for i := 0 to List.Count - 1 do
  3128. begin
  3129. Member := TPasElement(List[i]);
  3130. TREl := CreateTR(TableEl);
  3131. ParaEl := CreatePara(CreateTD(TREl));
  3132. case Member.Visibility of
  3133. visPrivate:
  3134. AppendText(ParaEl, 'pv');
  3135. visProtected:
  3136. AppendText(ParaEl, 'pt');
  3137. visPublished:
  3138. AppendText(ParaEl, 'pl');
  3139. end;
  3140. AppendNbSp(ParaEl, 1);
  3141. ParaEl := CreatePara(CreateTD(TREl));
  3142. if (Member.ClassType = TPasProperty) and
  3143. (Length(TPasProperty(Member).WriteAccessorName) = 0) then
  3144. begin
  3145. AppendText(ParaEl, 'ro');
  3146. AppendNbSp(ParaEl, 1);
  3147. end;
  3148. TDEl := CreateTD(TREl);
  3149. TDEl['nowrap'] := 'nowrap';
  3150. ParaEl := CreatePara(TDEl);
  3151. LinkEl := AppendHyperlink(ParaEl, Member);
  3152. if Assigned(LinkEl) then
  3153. LinkEl['onClick'] := 'opener.location.href = ''' + LinkEl['href'] +
  3154. '''; return false;';
  3155. AppendText(ParaEl, ' (');
  3156. LinkEl := AppendHyperlink(ParaEl, Member.Parent);
  3157. if Assigned(LinkEl) then
  3158. LinkEl['onClick'] := 'opener.location.href = ''' + LinkEl['href'] +
  3159. '''; return false;';
  3160. AppendText(ParaEl, ')');
  3161. end;
  3162. finally
  3163. List.Free;
  3164. end;
  3165. end;
  3166. begin
  3167. case ASubpageIndex of
  3168. 0:
  3169. CreateMainPage;
  3170. PropertiesByInheritanceSubindex:
  3171. CreateInheritanceSubpage(@PropertyFilter);
  3172. PropertiesByNameSubindex:
  3173. CreateSortedSubpage(@PropertyFilter);
  3174. MethodsByInheritanceSubindex:
  3175. CreateInheritanceSubpage(@MethodFilter);
  3176. MethodsByNameSubindex:
  3177. CreateSortedSubpage(@MethodFilter);
  3178. EventsByInheritanceSubindex:
  3179. CreateInheritanceSubpage(@EventFilter);
  3180. EventsByNameSubindex:
  3181. CreateSortedSubpage(@EventFilter);
  3182. end;
  3183. end;
  3184. procedure THTMLWriter.CreateClassMemberPageBody(AElement: TPasElement);
  3185. var
  3186. TableEl, TREl, CodeEl: TDOMElement;
  3187. procedure CreateVarPage(Element: TPasVariable);
  3188. begin
  3189. AppendHyperlink(CodeEl, Element.Parent);
  3190. AppendSym(CodeEl, '.');
  3191. AppendText(CodeEl, Element.Name);
  3192. if Assigned(Element.VarType) then
  3193. begin
  3194. AppendSym(CodeEl, ' : ');
  3195. AppendSym(AppendType(CodeEl, TableEl, Element.VarType, False), ';');
  3196. end;
  3197. end;
  3198. procedure CreateTypePage(Element: TPasType);
  3199. begin
  3200. AppendKw(CodeEl, 'type ');
  3201. AppendHyperlink(CodeEl, Element.Parent);
  3202. AppendSym(CodeEl, '.');
  3203. AppendText(CodeEl, Element.Name);
  3204. AppendSym(CodeEl, ' = ');
  3205. AppendTypeDecl(Element,TableEl,CodeEl)
  3206. end;
  3207. procedure CreateConstPage(Element: TPasConst);
  3208. begin
  3209. AppendKw(CodeEl, 'const ');
  3210. AppendHyperlink(CodeEl, Element.Parent);
  3211. AppendSym(CodeEl, '.');
  3212. AppendText(CodeEl, Element.Name);
  3213. if Assigned(Element.VarType) then
  3214. begin
  3215. AppendSym(CodeEl, ': ');
  3216. AppendType(CodeEl, TableEl, Element.VarType, False);
  3217. end;
  3218. AppendPasSHFragment(CodeEl, ' = ' + Element.Expr.GetDeclaration(True) + ';', 0);
  3219. end;
  3220. procedure CreatePropertyPage(Element: TPasProperty);
  3221. var
  3222. NeedBreak: Boolean;
  3223. T : TPasType;
  3224. begin
  3225. AppendKw(CodeEl, 'property ');
  3226. AppendHyperlink(CodeEl, Element.Parent);
  3227. AppendSym(CodeEl, '.');
  3228. AppendText(CodeEl, Element.Name);
  3229. T:=Element.ResolvedType;
  3230. if Assigned(T) then
  3231. begin
  3232. AppendSym(CodeEl, ' : ');
  3233. AppendType(CodeEl, TableEl, T, False);
  3234. end;
  3235. NeedBreak := False;
  3236. if Length(TPasProperty(Element).IndexValue) <> 0 then
  3237. begin
  3238. CreateEl(CodeEl, 'br');
  3239. AppendNbsp(CodeEl, 2);
  3240. AppendKw(CodeEl, 'index ');
  3241. AppendPasSHFragment(CodeEl, TPasProperty(Element).IndexValue, 0);
  3242. NeedBreak := True;
  3243. end;
  3244. if Length(TPasProperty(Element).ReadAccessorName) <> 0 then
  3245. begin
  3246. CreateEl(CodeEl, 'br');
  3247. AppendNbsp(CodeEl, 2);
  3248. AppendKw(CodeEl, 'read ');
  3249. AppendText(CodeEl, TPasProperty(Element).ReadAccessorName);
  3250. NeedBreak := True;
  3251. end;
  3252. if Length(TPasProperty(Element).WriteAccessorName) <> 0 then
  3253. begin
  3254. CreateEl(CodeEl, 'br');
  3255. AppendNbsp(CodeEl, 2);
  3256. AppendKw(CodeEl, 'write ');
  3257. AppendText(CodeEl, TPasProperty(Element).WriteAccessorName);
  3258. NeedBreak := True;
  3259. end;
  3260. if Length(TPasProperty(Element).StoredAccessorName) <> 0 then
  3261. begin
  3262. CreateEl(CodeEl, 'br');
  3263. AppendNbsp(CodeEl, 2);
  3264. AppendKw(CodeEl, 'stored ');
  3265. AppendText(CodeEl, TPasProperty(Element).StoredAccessorName);
  3266. NeedBreak := True;
  3267. end;
  3268. if Length(TPasProperty(Element).DefaultValue) <> 0 then
  3269. begin
  3270. CreateEl(CodeEl, 'br');
  3271. AppendNbsp(CodeEl, 2);
  3272. AppendKw(CodeEl, 'default ');
  3273. AppendPasSHFragment(CodeEl, TPasProperty(Element).DefaultValue, 0);
  3274. NeedBreak := True;
  3275. end;
  3276. AppendSym(CodeEl, ';');
  3277. if TPasProperty(Element).IsDefault or TPasProperty(Element).IsNodefault then
  3278. begin
  3279. if NeedBreak then
  3280. begin
  3281. CreateEl(CodeEl, 'br');
  3282. AppendNbsp(CodeEl, 2);
  3283. end;
  3284. if TPasProperty(Element).IsDefault then
  3285. AppendKw(CodeEl, 'default')
  3286. else
  3287. AppendKw(CodeEl, 'nodefault');
  3288. AppendSym(CodeEl, ';');
  3289. end;
  3290. end;
  3291. var
  3292. s: String;
  3293. DocNode: TDocNode;
  3294. begin
  3295. AppendMenuBar(-1);
  3296. AppendTitle(AElement.FullName);
  3297. AppendShortDescr(CreatePara(BodyElement), AElement);
  3298. AppendText(CreateH2(BodyElement), SDocDeclaration);
  3299. AppendSourceRef(AElement);
  3300. TableEl := CreateTable(BodyElement);
  3301. TREl := CreateTR(TableEl);
  3302. CodeEl := CreateCode(CreatePara(CreateTD(TREl)));
  3303. AppendText(CodeEl, ' '); // !!!: Workaround for current HTML writer
  3304. if (AElement.Visibility<>visDefault) then
  3305. begin
  3306. s:=VisibilityNames[AElement.Visibility];
  3307. AppendKw(CodeEl, s);
  3308. end;
  3309. AppendText(CodeEl, ' ');
  3310. if AElement is TPasProperty then
  3311. CreatePropertyPage(TPasProperty(AElement))
  3312. else if AElement is TPasConst then
  3313. CreateConstPage(TPasConst(AElement))
  3314. else if (AElement is TPasVariable) then
  3315. CreateVarPage(TPasVariable(AElement))
  3316. else if AElement is TPasProcedureBase then
  3317. AppendProcDecl(CodeEl, TableEl, TPasProcedureBase(AElement))
  3318. else if AElement is TPasType then
  3319. CreateTypePage(TPasType(AElement))
  3320. else
  3321. AppendText(CreateWarning(BodyElement), '<' + AElement.ClassName + '>');
  3322. FinishElementPage(AElement);
  3323. end;
  3324. procedure THTMLWriter.CreateVarPageBody(AVar: TPasVariable);
  3325. var
  3326. TableEl, TREl, TDEl, CodeEl, El: TDOMElement;
  3327. DocNode: TDocNode;
  3328. begin
  3329. AppendMenuBar(-1);
  3330. AppendTitle(AVar.FullName);
  3331. AppendShortDescr(CreatePara(BodyElement), AVar);
  3332. AppendText(CreateH2(BodyElement), SDocDeclaration);
  3333. AppendSourceRef(AVar);
  3334. TableEl := CreateTable(BodyElement);
  3335. TREl := CreateTR(TableEl);
  3336. TDEl := CreateTD(TREl);
  3337. CodeEl := CreateCode(CreatePara(TDEl));
  3338. AppendKw(CodeEl, 'var');
  3339. AppendText(CodeEl, ' ' + AVar.Name);
  3340. if Assigned(AVar.VarType) then
  3341. begin
  3342. AppendSym(CodeEl, ': ');
  3343. El := AppendType(CodeEl, TableEl, AVar.VarType, False);
  3344. end else
  3345. El := CodeEl;
  3346. if Length(AVar.Value) > 0 then
  3347. AppendPasSHFragment(El, ' = ' + AVar.Value + ';', 0)
  3348. else
  3349. AppendSym(El, ';');
  3350. FinishElementPage(AVar);
  3351. end;
  3352. procedure THTMLWriter.CreateProcPageBody(AProc: TPasProcedureBase);
  3353. var
  3354. TableEl, TREl, TDEl, CodeEl: TDOMElement;
  3355. begin
  3356. AppendMenuBar(-1);
  3357. AppendTitle(AProc.Name);
  3358. AppendShortDescr(CreatePara(BodyElement), AProc);
  3359. AppendText(CreateH2(BodyElement), SDocDeclaration);
  3360. AppendSourceRef(AProc);
  3361. TableEl := CreateTable(BodyElement);
  3362. TREl := CreateTR(TableEl);
  3363. TDEl := CreateTD(TREl);
  3364. CodeEl := CreateCode(CreatePara(TDEl));
  3365. AppendProcDecl(CodeEl, TableEl, AProc);
  3366. FinishElementPage(AProc);
  3367. end;
  3368. Function THTMLWriter.InterPretOption(Const Cmd,Arg : String) : boolean;
  3369. begin
  3370. Result:=True;
  3371. if Cmd = '--html-search' then
  3372. SearchPage := Arg
  3373. else if Cmd = '--footer' then
  3374. FooterFile := Arg
  3375. else if Cmd = '--charset' then
  3376. CharSet := Arg
  3377. else if Cmd = '--index-colcount' then
  3378. IndexColCount := StrToIntDef(Arg,IndexColCount)
  3379. else if Cmd = '--image-url' then
  3380. FBaseImageURL := Arg
  3381. else if Cmd = '--css-file' then
  3382. FCSSFile := arg
  3383. else if Cmd = '--footer-date' then
  3384. begin
  3385. FIDF:=True;
  3386. FDateFormat:=Arg;
  3387. end
  3388. else if Cmd = '--disable-menu-brackets' then
  3389. FUseMenuBrackets:=False
  3390. else
  3391. Result:=False;
  3392. end;
  3393. procedure THTMLWriter.WriteDoc;
  3394. begin
  3395. DoLog(SWritingPages, [PageCount]);
  3396. WriteHTMLPages;
  3397. end;
  3398. class procedure THTMLWriter.Usage(List: TStrings);
  3399. begin
  3400. List.add('--footer');
  3401. List.Add(SHTMLUsageFooter);
  3402. List.Add('--footer-date[=Fmt]');
  3403. List.Add(SHTMLUsageFooterDate);
  3404. List.Add('--charset=set');
  3405. List.Add(SHTMLUsageCharset);
  3406. List.Add('--html-search=pagename');
  3407. List.Add(SHTMLHtmlSearch);
  3408. List.Add('--index-colcount=N');
  3409. List.Add(SHTMLIndexColcount);
  3410. List.Add('--image-url=url');
  3411. List.Add(SHTMLImageUrl);
  3412. List.Add('--disable-menu-brackets');
  3413. List.Add(SHTMLDisableMenuBrackets);
  3414. end;
  3415. class procedure THTMLWriter.SplitImport(var AFilename, ALinkPrefix: String);
  3416. var
  3417. i: integer;
  3418. begin
  3419. i := Pos(',', AFilename);
  3420. if i > 0 then
  3421. begin //split into filename and prefix
  3422. ALinkPrefix := Copy(AFilename,i+1,Length(AFilename));
  3423. SetLength(AFilename, i-1);
  3424. end
  3425. else if ALinkPrefix = '' then
  3426. begin //synthesize outdir\pgk.xct, ..\pkg
  3427. ALinkPrefix := '../' + ChangeFileExt(ExtractFileName(AFilename), '');
  3428. AFilename := ChangeFileExt(AFilename, '.xct');
  3429. end;
  3430. end;
  3431. Class Function THTMLWriter.FileNameExtension : String;
  3432. begin
  3433. result:='';
  3434. end;
  3435. // private methods
  3436. function THTMLWriter.GetPageCount: Integer;
  3437. begin
  3438. Result := PageInfos.Count;
  3439. end;
  3440. procedure THTMLWriter.SetOnTest(const AValue: TNotifyEvent);
  3441. begin
  3442. if FOnTest=AValue then exit;
  3443. FOnTest:=AValue;
  3444. end;
  3445. procedure THTMLWriter.CreateAllocator;
  3446. begin
  3447. FAllocator:=TLongNameFileAllocator.Create('.html');
  3448. end;
  3449. procedure THTMWriter.CreateAllocator;
  3450. begin
  3451. FAllocator:=TShortNameFileAllocator.Create('.htm');
  3452. end;
  3453. initialization
  3454. // Do not localize.
  3455. RegisterWriter(THTMLWriter,'html','HTML output using fpdoc.css stylesheet.');
  3456. RegisterWriter(THTMWriter,'htm','HTM (8.3 filenames) output using fpdoc.css stylesheet.');
  3457. RegisterWriter(TCHMHTMLWriter,'chm','Compressed HTML file output using fpdoc.css stylesheet.');
  3458. finalization
  3459. UnRegisterWriter('html');
  3460. UnRegisterWriter('htm');
  3461. UnRegisterWriter('chm');
  3462. end.