cc865498154ffed71eb59a237d5ec48836c3dd19
1 # This file is part of NIT ( http://www.nitlanguage.org ).
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
7 # http://www.apache.org/licenses/LICENSE-2.0
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.
15 # HTML templates used by Nitdoc to generate API documentation
16 # Pages are assembled using `Template`
21 # A documentation page
25 # Page title in HTML header
26 var title
: String writable
28 # Directory where css, js and other assets can be found
29 var shareurl
: String writable
31 # Attributes of the body tag element
32 var body_attrs
= new Array[TagAttribute]
34 # Top menu template if any
35 var topmenu
: TplTopMenu writable
37 # Sidebar template if any
38 var sidebar
: nullable TplSidebar writable
40 # Content of the page in form a TplSection
41 var sections
= new Array[TplSection]
43 # Footer content if any
44 var footer
: nullable Streamable writable
46 # JS scripts to append at the end of the body
47 var scripts
= new Array[TplScript]
51 # Add a section to this page
52 fun add_section
(section
: TplSection) do
56 # Render the html header
57 private fun render_head
do
60 add
" <meta charset='utf-8'/>"
61 add
" <!--link rel='stylesheet' href='{shareurl}/css/Nitdoc.UI.css' type='text/css'/-->"
62 add
" <link rel='stylesheet' href='{shareurl}/vendors/bootstrap/css/bootstrap.min.css'/>"
63 add
" <link rel='stylesheet' href='{shareurl}/css/nitdoc.bootstrap.css'/>"
64 add
" <link rel='stylesheet' href='{shareurl}/css/nitdoc.css'/>"
65 add
" <link rel='stylesheet' href='{shareurl}/css/Nitdoc.QuickSearch.css'/>"
66 add
" <link rel='stylesheet' href='{shareurl}/css/Nitdoc.ModalBox.css'/>"
67 add
" <link rel='stylesheet' href='{shareurl}/css/Nitdoc.GitHub.css'/>"
68 add
" <title>{title}</title>"
71 for attr
in body_attrs
do add attr
75 # Render the topmenu template
76 private fun render_topmenu
do
77 add
" <div class='row'>"
83 # Sidebar is automatically populated with a summary of all sections
85 if sidebar
== null then return
86 var summary
= new TplSummary.with_order
(0)
87 for section
in sections
do
88 section
.render_summary summary
90 sidebar
.boxes
.add summary
91 add sidebar
.as(not null)
93 # Render the footer and content
94 private fun render_content
do
95 for section
in sections
do add section
96 if footer
!= null then
97 add
"<div class='well footer'>"
98 add footer
.as(not null)
104 private fun render_footer
do
105 add
"<script src='{shareurl}/vendors/jquery/jquery-1.11.1.min.js'></script>"
106 add
"<script src='{shareurl}/vendors/jquery/jquery-ui-1.10.4.custom.min.js'></script>"
107 add
"<script src='{shareurl}/vendors/bootstrap/js/bootstrap.min.js'></script>"
108 add
"<script data-main='{shareurl}/js/nitdoc' src='{shareurl}/js/lib/require.js'</script>"
109 for script
in scripts
do add script
112 $("[data-toggle='tooltip']").tooltip();
113 $("[data-toggle='popover']").popover();
120 # Render the whole page
121 redef fun rendering
do
123 add
"<div class='container-fluid'>"
125 add
" <div class='row' id='content'>"
126 if sidebar
!= null then
127 add
"<div class='col col-xs-3 col-lg-2'>"
130 add
"<div class='col col-xs-9 col-lg-10' data-spy='scroll' data-target='.summary'>"
134 add
"<div class='col col-xs-12'>"
144 #########################
145 # general layout elements
146 #########################
148 # Top menu bar template
152 # Brand link to display in first position of the top menu
153 private var brand
: nullable Streamable writable
154 # Elements of the topmenu
155 private var elts
= new Array[Streamable]
159 # Add a content between `<li>` tags
160 fun add_item
(content
: Streamable, is_active
: Bool) do
161 var tpl
= new Template
164 tpl
.add
" class='active'"
172 # Add a raw content to the menu
173 fun add_raw
(content
: Streamable) do
177 redef fun rendering
do
178 if brand
== null and elts
.is_empty
then return
179 add
"<nav id='topmenu' class='navbar navbar-default navbar-fixed-top' role='navigation'>"
180 add
" <div class='container-fluid'>"
181 add
" <div class='navbar-header'>"
182 add
" <button type='button' class='navbar-toggle' "
183 add
" data-toggle='collapse' data-target='#topmenu-collapse'>"
184 add
" <span class='sr-only'>Toggle menu</span>"
185 add
" <span class='icon-bar'></span>"
186 add
" <span class='icon-bar'></span>"
187 add
" <span class='icon-bar'></span>"
189 if brand
!= null then add brand
.as(not null)
191 add
" <div class='collapse navbar-collapse' id='topmenu-collapse'>"
192 if not elts
.is_empty
then
193 add
"<ul class='nav navbar-nav'>"
194 for elt
in elts
do add elt
207 # Sidebar contains sidebar element templates called boxes
208 var boxes
= new Array[TplSidebarElt]
210 # Sort boxes by order priority
211 private fun order_boxes
do
212 var sorter
= new OrderComparator
216 redef fun rendering
do
217 if boxes
.is_empty
then return
219 add
"<div id='sidebar'>"
220 for box
in boxes
do add box
225 # Comparator used to sort boxes by order
226 private class OrderComparator
227 super Comparator[TplSidebarElt]
229 redef fun compare
(a
, b
) do
230 if a
.order
< b
.order
then return -1
231 if a
.order
> b
.order
then return 1
236 # Something that can be put in the sidebar
240 # Order of the box in the sidebar
243 init with_order
(order
: Int) do self.order
= order
246 # Agenericbox that can be added to sidebar
250 # Title of the box to display
251 # Title is also a placeholder for the collapse link
255 # equals to `title.to_cmangle` by default
256 # Used for collapsing
259 # Content to display in the box
260 # box will not be rendered if the content is null
261 var content
: nullable Streamable writable
263 # Is the box opened by default
264 # otherwise, the user will have to clic on the title to display the content
265 var is_open
writable = false
267 init(title
: String) do
269 self.id
= title
.to_cmangle
272 init with_content
(title
: String, content
: Streamable) do
274 self.content
= content
277 redef fun rendering
do
278 if content
== null then return
280 if is_open
then open
= "in"
281 add
"<div class='panel'>"
282 add
" <div class='panel-heading'>"
283 add
" <a data-toggle='collapse' data-parent='#sidebar' data-target='#box_{id}' href='#'>"
287 add
" <div id='box_{id}' class='panel-body collapse {open}'>"
288 add content
.as(not null)
294 # Something that can go on a summary template
298 # Add an element to the summary
299 fun add_child
(child
: TplSummaryElt) is abstract
302 # A summary that can go on the sidebar
303 # If the page contains a sidebar, the summary is automatically placed
304 # on top of the sidebarauto-generated
305 # summary contains anchors to all sections displayed in the page
310 # Summary elements to display
311 var children
= new Array[TplSummaryElt]
313 redef fun add_child
(child
) do children
.add child
315 redef fun rendering
do
316 if children
.is_empty
then return
317 add
"<div class='panel'>"
318 add
" <div class='panel-heading'>"
319 add
" <a data-toggle='collapse' data-parent='#sidebar' data-target='#box-sum' href='#'>"
323 add
" <div id='box-sum' class='summary collapse in'>"
324 add
" <ul class='nav'>"
325 for entry
in children
do add entry
333 class TplSummaryEntry
339 # Children of this entry
340 # Will be displayed as a tree
341 var children
= new Array[TplSummaryElt]
343 init(text
: Streamable) do self.text
= text
345 redef fun add_child
(child
) do children
.add child
347 redef fun rendering
do
350 if not children
.is_empty
then
351 add
"<ul class='nav'>"
352 for entry
in children
do add entry
359 # Something that can go in a section
360 # Sections are automatically collected to populate the menu
367 # Title to display if any
368 # if both `title` and `summary_title` are null then
369 # the section will not appear in the summary
370 var title
: nullable Streamable writable
372 # Subtitle to display if any
373 var subtitle
: nullable Streamable writable
375 # Title that appear in the summary
376 # if null use `title` instead
377 var summary_title
: nullable String writable
379 # Parent section of this section if any
380 var parent
: nullable TplSection
382 init(id
: String) do self.id
= id
384 init with_title
(id
: String, title
: Streamable) do
389 # Level <hX> for HTML heading
390 protected fun hlvl
: Int do
391 if parent
== null then return 1
392 return parent
.hlvl
+ 1
395 # Render this section in the summary
396 protected fun render_summary
(parent
: TplSummaryElt) is abstract
398 # Is the section empty (no content at all)
399 fun is_empty
: Bool is abstract
402 # A HTML <section> element
406 # Elements contained by this section
407 var children
= new Array[TplSectionElt]
409 # Add an element in this section
410 fun add_child
(child
: TplSectionElt) do
415 redef fun is_empty
: Bool do return children
.is_empty
417 redef fun render_summary
(parent
) do
418 if is_empty
then return
419 var title
= summary_title
420 if title
== null and self.title
!= null then title
= self.title
.write_to_string
421 if title
== null then return
422 var lnk
= new TplLink("#{id}", title
)
423 var entry
= new TplSummaryEntry(lnk
)
424 for child
in children
do
425 child
.render_summary
(entry
)
427 parent
.add_child entry
430 redef fun rendering
do
431 add
"<section id='{id}'>"
432 if title
!= null then
435 add title
.as(not null)
438 if subtitle
!= null then
439 add
"<div class='info subtitle'>"
440 add subtitle
.as(not null)
443 for child
in children
do
450 # A page article that can go in a section
454 # Content for this article
455 var content
: nullable Streamable writable = null
456 var source_link
: nullable Streamable writable = null
458 init with_content
(id
: String, title
: Streamable, content
: Streamable) do
459 with_title
(id
, title
)
460 self.content
= content
463 # CSS classes to apply on the article title heading element
464 var title_classes
= new Array[String]
466 redef fun render_summary
(parent
) do
467 if is_empty
then return
468 var title
= summary_title
469 if title
== null and self.title
!= null then title
= self.title
.write_to_string
470 if title
== null then return
471 var lnk
= new TplLink("#{id}", title
)
472 parent
.add_child
new TplSummaryEntry(lnk
)
475 redef fun rendering
do
476 if is_empty
then return
477 add
"<article id='{id}'>"
478 if title
!= null then
480 add
"<h{lvl} class='{title_classes.join(" ")}'>"
481 add title
.as(not null)
484 if subtitle
!= null then
485 add
"<div class='info subtitle'>"
486 add subtitle
.as(not null)
489 if content
!= null then
490 add content
.as(not null)
495 redef fun is_empty
: Bool do
496 return title
== null and subtitle
== null and content
== null
500 # A module / class / prop definition
505 var comment
: nullable Streamable writable
507 # Namespace for this definition
508 var namespace
: nullable Streamable writable
510 # Location link to display
511 var location
: nullable Streamable writable
515 private fun render_info
do
516 add
"<div class='info text-right'>"
517 if namespace
!= null then
518 if comment
== null then
519 add
"<span class=\"noComment\
">no comment for </span>"
521 add namespace
.as(not null)
523 if location
!= null then
525 add location
.as(not null)
530 private fun render_comment
do
531 if comment
!= null then add comment
.as(not null)
534 redef fun rendering
do
535 add
"<div class='definition'>"
543 class TplClassDefinition
546 var intros
= new Array[TplListElt]
547 var redefs
= new Array[TplListElt]
551 redef fun rendering
do
552 add
"<div class='definition'>"
555 render_list
("Introduces", intros
)
556 render_list
("Redefines", redefs
)
560 private fun render_list
(name
: String, elts
: Array[TplListElt]) do
561 if elts
.is_empty
then return
562 add
"<h5>{name}</h5>"
563 add
"<ul class='list-unstyled list-definition'>"
564 for elt
in elts
do add elt
569 # Layout for Search page
573 var modules
= new Array[Streamable]
574 var classes
= new Array[Streamable]
575 var props
= new Array[Streamable]
577 redef fun rendering
do
578 if title
!= null then add
"<h1>{title}</h1>"
579 add
"<div class='container-fluid'>"
580 add
" <div class='row'>"
581 if not modules
.is_empty
then
582 add
"<div class='col-xs-4'>"
583 add
"<h3>Modules</h3>"
593 if not classes
.is_empty
then
594 add
"<div class='col-xs-4'>"
595 add
"<h3>Classes</h3>"
605 if not props
.is_empty
then
606 add
"<div class='col-xs-4'>"
607 add
"<h3>Properties</h3>"
622 #####################
623 # Basiv HTML elements
624 #####################
631 var href
: String writable
633 # Text to display in the link
634 var text
: String writable
637 var title
: nullable String writable
639 init(href
, text
: String) do
644 init with_title
(href
, text
, title
: String) do
649 redef fun rendering
do
653 if title
!= null then
655 add title.as(not null)
668 # Elements contained in this list
669 # can be <li> or <ul> elements
670 var elts
= new Array[TplListElt]
672 # CSS classes of the <ul> element
673 var css_classes
= new Array[String]
675 # Add content wrapped in a <li> element
676 fun add_li
(content
: Streamable) do elts
.add
new TplListItem.with_content
(content
)
680 init with_classes
(classes
: Array[String]) do self.css_classes
= classes
682 redef fun rendering
do
683 if elts
.is_empty
then return
684 add
"<ul class='{css_classes.join(" ")}'>"
685 for elt
in elts
do add elt
690 # Something that can be added to a TplList
699 # Content of the list item
700 var content
= new Template
702 # CSS classes of the <li> element
703 var css_classes
= new Array[String]
707 init with_content
(content
: Streamable) do append
(content
)
709 init with_classes
(content
: Streamable, classes
: Array[String]) do
710 with_content
(content
)
711 css_classes
= classes
714 # Append `content` to the item
715 # similar to `self.content.add`
716 fun append
(content
: Streamable) do self.content
.add content
718 redef fun rendering
do
720 for cls
in css_classes
do add
" {cls}"
727 # A label with a text content
731 # Content of the label if any
732 var content
: nullable Streamable
734 # CSS classes of the <span> element
735 var css_classes
= new Array[String]
738 init with_content
(content
: Streamable) do self.content
= content
739 init with_classes
(classes
: Array[String]) do self.css_classes
= classes
741 redef fun rendering
do
742 add
"<span class='label {css_classes.join(" ")}'>"
743 if content
!= null then add content
.as(not null)
748 # A label with an icon
753 # see: http://getbootstrap.com/components/#glyphicons
756 init with_icon
(icon
: String) do self.icon
= icon
758 redef fun rendering
do
759 add
"<span class='glyphicon glyphicon-{icon} {css_classes.join(" ")}'>"
760 if content
!= null then add content
.as(not null)
765 # A HTML tag attribute
766 # `<tag attr="value">`
771 var value
: nullable String
773 init(name
: String, value
: nullable String) do
778 redef fun rendering
do
779 if value
== null then
782 add
(" {name}=\"{value}\
"")
791 var attrs
= new Array[TagAttribute]
792 var content
: nullable Streamable writable
795 attrs
.add
(new TagAttribute("type", "text/javascript"))
798 protected fun render_content
do
799 if content
!= null then add content
.as(not null)
802 redef fun rendering
do
804 for attr
in attrs
do add attr
811 # JS script for Piwik Tracker
815 var tracker_url
: String
818 init(tracker_url
, site_id
: String) do
820 self.tracker_url
= tracker_url
821 self.site_id
= site_id
824 redef fun render_content
do
826 add
"var _paq = _paq || [];"
827 add
" _paq.push([\"trackPageView\
"]);"
828 add
" _paq.push([\"enableLinkTracking\
"]);"
830 add
" var u=((\"https
:\
" == document.location.protocol) ? \"https\
" : \"http\
") + \"://{tracker_url}\
";"
831 add
" _paq.push([\"setTrackerUrl\
", u+\"piwik
.php\
"]);"
832 add
" _paq.push([\"setSiteId\
", \"{site_id}\
"]);"
833 add
" var d=document, g=d.createElement(\"script\
"), s=d.getElementsByTagName(\"script\
")[0]; g.type=\"text
/javascript\
";"
834 add
" g.defer=true; g.async=true; g.src=u+\"piwik
.js\
"; s.parentNode.insertBefore(g,s);"