src/doc: migrate Overview page to `doc_phases`
[nit.git] / src / doc / doc_phases / doc_structure.nit
1 # This file is part of NIT ( http://www.nitlanguage.org ).
2 #
3 # Licensed under the Apache License, Version 2.0 (the "License");
4 # you may not use this file except in compliance with the License.
5 # You may obtain a copy of the License at
6 #
7 # http://www.apache.org/licenses/LICENSE-2.0
8 #
9 # Unless required by applicable law or agreed to in writing, software
10 # distributed under the License is distributed on an "AS IS" BASIS,
11 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 # See the License for the specific language governing permissions and
13 # limitations under the License.
14
15 # Composes the DocComposite tree of a DocPage and organizes its content.
16 module doc_structure
17
18 import doc_concerns
19
20 # StructurePhase populates the DocPage content with section and article.
21 #
22 # This phase only applies structure.
23 # The content of the structure is choosen by the rendering phases.
24 class StructurePhase
25 super DocPhase
26
27 # Used to sort ConcernsTree by rank.
28 private var concerns_sorter = new MConcernRankSorter
29
30 # Used to sort ConcernsTree by name.
31 private var name_sorter = new MEntityNameSorter
32
33 # Populates the given DocModel.
34 redef fun apply do
35 for page in doc.pages do page.apply_structure(self, doc)
36 end
37
38 # TODO index and search page should also be structured here
39 end
40
41 redef class DocPage
42
43 # Populates `self` with structure elements like DocComposite ones.
44 #
45 # See `StructurePhase`.
46 fun apply_structure(v: StructurePhase, doc: DocModel) do end
47 end
48
49 redef class OverviewPage
50 redef fun apply_structure(v, doc) do
51 var article = new HomeArticle
52 root.add_child article
53 # Projects list
54 var mprojects = doc.model.mprojects.to_a
55 var sorter = new MConcernRankSorter
56 sorter.sort mprojects
57 var section = new ProjectsSection
58 for mproject in mprojects do
59 section.add_child new DefinitionArticle(mproject)
60 end
61 article.add_child section
62 end
63 end
64
65 redef class MGroupPage
66 redef fun apply_structure(v, doc) do
67 var section = new MEntitySection(mentity)
68 root.add_child section
69 if mentity.is_root then
70 section.add_child new IntroArticle(mentity.mproject)
71 else
72 section.add_child new IntroArticle(mentity)
73 end
74 var concerns = self.concerns
75 if concerns == null or concerns.is_empty then return
76 # FIXME avoid diff
77 mentity.mproject.booster_rank = -1000
78 mentity.booster_rank = -1000
79 concerns.sort_with(v.concerns_sorter)
80 mentity.mproject.booster_rank = 0
81 mentity.booster_rank = 0
82 section.add_child new ConcernsArticle(mentity, concerns)
83 for mentity in concerns do
84 if mentity isa MModule then
85 section.add_child new DefinitionArticle(mentity)
86 else
87 section.add_child new ConcernSection(mentity)
88 end
89 end
90 end
91 end
92
93 redef class MModulePage
94 redef fun apply_structure(v, doc) do
95 var section = new MEntitySection(mentity)
96 root.add_child section
97 section.add_child new IntroArticle(mentity)
98 var concerns = self.concerns
99 if concerns == null or concerns.is_empty then return
100 # FIXME avoid diff
101 mentity.mgroup.mproject.booster_rank = -1000
102 mentity.mgroup.booster_rank = -1000
103 mentity.booster_rank = -1000
104 concerns.sort_with(v.concerns_sorter)
105 mentity.mgroup.mproject.booster_rank = 0
106 mentity.mgroup.booster_rank = 0
107 mentity.booster_rank = 0
108 section.add_child new ConcernsArticle(mentity, concerns)
109 # reference list
110 for mentity in concerns do
111 var ssection = new ConcernSection(mentity)
112 if mentity isa MModule then
113 var mclasses = mclasses_for_mmodule(mentity).to_a
114 v.name_sorter.sort(mclasses)
115 for mclass in mclasses do
116 var article = new DefinitionArticle(mclass)
117 var mclassdefs = mclassdefs_for(mclass).to_a
118 if not mclassdefs.has(mclass.intro) then
119 article.add_child(new DefinitionArticle(mclass.intro))
120 end
121 doc.mainmodule.linearize_mclassdefs(mclassdefs)
122 for mclassdef in mclassdefs do
123 article.add_child(new DefinitionArticle(mclassdef))
124 end
125 ssection.add_child article
126 end
127 end
128 section.add_child ssection
129 end
130 end
131
132 # Filters `self.mclassses` by intro `mmodule`.
133 private fun mclasses_for_mmodule(mmodule: MModule): Set[MClass] do
134 var mclasses = new HashSet[MClass]
135 for mclass in self.mclasses do
136 if mclass.intro.mmodule == mmodule then
137 mclasses.add mclass
138 end
139 end
140 return mclasses
141 end
142
143 # Filters `self.mclassdefs` by `mclass`.
144 private fun mclassdefs_for(mclass: MClass): Set[MClassDef] do
145 var mclassdefs = new HashSet[MClassDef]
146 for mclassdef in self.mclassdefs do
147 if mclassdef.mclass == mclass then
148 mclassdefs.add mclassdef
149 end
150 end
151 return mclassdefs
152 end
153 end
154
155 redef class MClassPage
156 redef fun apply_structure(v, doc) do
157 var section = new MEntitySection(mentity)
158 root.add_child section
159 section.add_child new IntroArticle(mentity)
160 var concerns = self.concerns
161 if concerns == null or concerns.is_empty then return
162 # FIXME diff hack
163 mentity.intro_mmodule.mgroup.mproject.booster_rank = -1000
164 mentity.intro_mmodule.mgroup.booster_rank = -1000
165 mentity.intro_mmodule.booster_rank = -1000
166 concerns.sort_with(v.concerns_sorter)
167 mentity.intro_mmodule.mgroup.mproject.booster_rank = 0
168 mentity.intro_mmodule.mgroup.booster_rank = 0
169 mentity.intro_mmodule.booster_rank = 0
170 section.add_child new ConcernsArticle(mentity, concerns)
171 for mentity in concerns do
172 var ssection = new ConcernSection(mentity)
173 if mentity isa MModule then
174 var mprops = mproperties_for(mentity)
175 var by_kind = new PropertiesByKind.with_elements(mprops)
176 for group in by_kind.groups do
177 v.name_sorter.sort(group)
178 for mprop in group do
179 for mpropdef in mpropdefs_for(mprop, mentity) do
180 ssection.add_child new DefinitionArticle(mpropdef)
181 end
182 end
183 end
184 end
185 section.add_child ssection
186 end
187 end
188
189 # Filters `self.mpropdefs` by `mmodule`.
190 #
191 # FIXME diff hack
192 private fun mproperties_for(mmodule: MModule): Set[MProperty] do
193 var mprops = new HashSet[MProperty]
194 for mpropdef in self.mpropdefs do
195 if mpropdef.mclassdef.mmodule == mmodule then
196 mprops.add mpropdef.mproperty
197 end
198 end
199 return mprops
200 end
201
202 # Filters `self.mpropdefs` by `mproperty`.
203 #
204 # FIXME diff hack
205 private fun mpropdefs_for(mproperty: MProperty, mmodule: MModule): Set[MPropDef] do
206 var mpropdefs = new HashSet[MPropDef]
207 for mpropdef in self.mpropdefs do
208 if mpropdef.mproperty == mproperty and
209 mpropdef.mclassdef.mmodule == mmodule then
210 mpropdefs.add mpropdef
211 end
212 end
213 return mpropdefs
214 end
215 end
216
217 redef class MPropertyPage
218 redef fun apply_structure(v, doc) do
219 var section = new MEntitySection(mentity)
220 root.add_child section
221 section.add_child new IntroArticle(mentity)
222 var concerns = self.concerns
223 if concerns == null or concerns.is_empty then return
224 # FIXME diff hack
225 mentity.intro.mclassdef.mmodule.mgroup.mproject.booster_rank = -1000
226 mentity.intro.mclassdef.mmodule.mgroup.booster_rank = -1000
227 mentity.intro.mclassdef.mmodule.booster_rank = -1000
228 concerns.sort_with(v.concerns_sorter)
229 mentity.intro.mclassdef.mmodule.mgroup.mproject.booster_rank = 0
230 mentity.intro.mclassdef.mmodule.mgroup.booster_rank = 0
231 mentity.intro.mclassdef.mmodule.booster_rank = 0
232 section.add_child new ConcernsArticle(mentity, concerns)
233 for mentity in concerns do
234 var ssection = new ConcernSection(mentity)
235 if mentity isa MModule then
236 # Add mproperties
237 var mpropdefs = mpropdefs_for(mentity).to_a
238 v.name_sorter.sort(mpropdefs)
239 for mpropdef in mpropdefs do
240 ssection.add_child new DefinitionArticle(mpropdef)
241 end
242 end
243 section.add_child ssection
244 end
245 end
246
247 # Filters `self.mpropdefs` by `mmodule`.
248 private fun mpropdefs_for(mmodule: MModule): Set[MPropDef] do
249 var mpropdefs = new HashSet[MPropDef]
250 for mpropdef in self.mpropdefs do
251 if mpropdef.mclassdef.mmodule == mmodule then
252 mpropdefs.add mpropdef
253 end
254 end
255 return mpropdefs
256 end
257 end
258
259 # A DocComposite element about a MEntity.
260 class MEntityComposite
261 super DocComposite
262
263 # MEntity documented by this page element.
264 var mentity: MEntity
265 end
266
267 # A Section about a Concern.
268 #
269 # Those sections are used to build the page summary.
270 class ConcernSection
271 super MEntityComposite
272 super DocSection
273 end
274
275 # An article about a Mentity.
276 #
277 # Used to display textual content about a MEntity.
278 abstract class MEntityArticle
279 super MEntityComposite
280 super DocArticle
281 end
282
283 # A section about a Mentity.
284 #
285 # Used to regroup content about a MEntity.
286 class MEntitySection
287 super MEntityComposite
288 super DocSection
289 end
290
291 # An introduction article about a MEntity.
292 #
293 # Used at the top of a documentation page to introduce the documented MEntity.
294 class IntroArticle
295 super MEntityComposite
296 super DocArticle
297 end
298
299 # An article that display a ConcernsTreee as a list.
300 class ConcernsArticle
301 super MEntityArticle
302
303 # Concerns to list in this article.
304 var concerns: ConcernsTree
305 end
306
307 # An article that display the definition text of a MEntity.
308 class DefinitionArticle
309 super MEntityArticle
310 end
311
312 # The main project article.
313 class HomeArticle
314 super DocArticle
315 end
316
317 # The project list.
318 class ProjectsSection
319 super DocArticle
320 end