summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--ocamldoc/odoc_html.ml1577
-rw-r--r--ocamldoc/odoc_ocamlhtml.mll88
2 files changed, 859 insertions, 806 deletions
diff --git a/ocamldoc/odoc_html.ml b/ocamldoc/odoc_html.ml
index 014804576..8289eb178 100644
--- a/ocamldoc/odoc_html.ml
+++ b/ocamldoc/odoc_html.ml
@@ -120,9 +120,8 @@ module Naming =
(** A class with a method to colorize a string which represents OCaml code. *)
class ocaml_code =
object(self)
- method html_of_code ?(with_pre=true) code =
- let html_code = Odoc_ocamlhtml.html_of_code ~with_pre: with_pre code in
- html_code
+ method html_of_code fmt ?(with_pre=true) code =
+ Odoc_ocamlhtml.html_of_code fmt ~with_pre: with_pre code
end
@@ -136,98 +135,143 @@ class text =
make some replacements (double newlines replaced by <br>). *)
method escape s = Odoc_ocamlhtml.escape_base s
- (** Return the html code corresponding to the [text] parameter. *)
- method html_of_text t = String.concat "" (List.map self#html_of_text_element t)
+ (** Print the html code corresponding to the [text] parameter. *)
+ method html_of_text fmt t = List.iter (self#html_of_text_element fmt) t
- (** Return the html code for the [text_element] in parameter. *)
- method html_of_text_element te =
+ (** Print the html code for the [text_element] in parameter. *)
+ method html_of_text_element fmt te =
print_DEBUG "text::html_of_text_element";
match te with
- | Odoc_info.Raw s -> self#html_of_Raw s
- | Odoc_info.Code s -> self#html_of_Code s
- | Odoc_info.CodePre s -> self#html_of_CodePre s
- | Odoc_info.Verbatim s -> self#html_of_Verbatim s
- | Odoc_info.Bold t -> self#html_of_Bold t
- | Odoc_info.Italic t -> self#html_of_Italic t
- | Odoc_info.Emphasize t -> self#html_of_Emphasize t
- | Odoc_info.Center t -> self#html_of_Center t
- | Odoc_info.Left t -> self#html_of_Left t
- | Odoc_info.Right t -> self#html_of_Right t
- | Odoc_info.List tl -> self#html_of_List tl
- | Odoc_info.Enum tl -> self#html_of_Enum tl
- | Odoc_info.Newline -> self#html_of_Newline
- | Odoc_info.Block t -> self#html_of_Block t
- | Odoc_info.Title (n, l_opt, t) -> self#html_of_Title n l_opt t
- | Odoc_info.Latex s -> self#html_of_Latex s
- | Odoc_info.Link (s, t) -> self#html_of_Link s t
- | Odoc_info.Ref (name, ref_opt) -> self#html_of_Ref name ref_opt
- | Odoc_info.Superscript t -> self#html_of_Superscript t
- | Odoc_info.Subscript t -> self#html_of_Subscript t
-
- method html_of_Raw s = self#escape s
-
- method html_of_Code s =
+ | Odoc_info.Raw s -> self#html_of_Raw fmt s
+ | Odoc_info.Code s -> self#html_of_Code fmt s
+ | Odoc_info.CodePre s -> self#html_of_CodePre fmt s
+ | Odoc_info.Verbatim s -> self#html_of_Verbatim fmt s
+ | Odoc_info.Bold t -> self#html_of_Bold fmt t
+ | Odoc_info.Italic t -> self#html_of_Italic fmt t
+ | Odoc_info.Emphasize t -> self#html_of_Emphasize fmt t
+ | Odoc_info.Center t -> self#html_of_Center fmt t
+ | Odoc_info.Left t -> self#html_of_Left fmt t
+ | Odoc_info.Right t -> self#html_of_Right fmt t
+ | Odoc_info.List tl -> self#html_of_List fmt tl
+ | Odoc_info.Enum tl -> self#html_of_Enum fmt tl
+ | Odoc_info.Newline -> self#html_of_Newline fmt
+ | Odoc_info.Block t -> self#html_of_Block fmt t
+ | Odoc_info.Title (n, l_opt, t) -> self#html_of_Title fmt n l_opt t
+ | Odoc_info.Latex s -> self#html_of_Latex fmt s
+ | Odoc_info.Link (s, t) -> self#html_of_Link fmt s t
+ | Odoc_info.Ref (name, ref_opt) -> self#html_of_Ref fmt name ref_opt
+ | Odoc_info.Superscript t -> self#html_of_Superscript fmt t
+ | Odoc_info.Subscript t -> self#html_of_Subscript fmt t
+
+ method html_of_Raw fmt s =
+ Format.pp_print_string fmt (self#escape s)
+
+ method html_of_Code fmt s =
if !Odoc_args.colorize_code then
- self#html_of_code ~with_pre: false s
+ self#html_of_code fmt ~with_pre: false s
else
- "<code class=\""^Odoc_ocamlhtml.code_class^"\">"^(self#escape s)^"</code>"
+ Format.fprintf fmt "@{<code class=\"%s\">%s@}" Odoc_ocamlhtml.code_class (self#escape s)
- method html_of_CodePre s =
+ method html_of_CodePre fmt s =
+ Format.fprintf fmt "@{<pre>";
if !Odoc_args.colorize_code then
- "<pre></pre>"^(self#html_of_code s)^"<pre></pre>"
+ (
+ Format.fprintf fmt "@}";
+ self#html_of_code fmt s;
+ Format.fprintf fmt "@{<pre>"
+ )
else
- "<pre><code class=\""^Odoc_ocamlhtml.code_class^"\">"^(self#escape s)^"</code></pre>"
-
- method html_of_Verbatim s = "<pre>"^(self#escape s)^"</pre>"
- method html_of_Bold t = "<b>"^(self#html_of_text t)^"</b>"
- method html_of_Italic t = "<i>"^(self#html_of_text t)^"</i>"
- method html_of_Emphasize t = "<em>"^(self#html_of_text t)^"</em>"
- method html_of_Center t = "<center>"^(self#html_of_text t)^"</center>"
- method html_of_Left t = "<div align=left>"^(self#html_of_text t)^"</div>"
- method html_of_Right t = "<div align=right>"^(self#html_of_text t)^"</div>"
-
- method html_of_List tl =
- "<ul>\n"^
- (String.concat ""
- (List.map (fun t -> "<li>"^(self#html_of_text t)^"</li>\n") tl))^
- "</ul>\n"
-
- method html_of_Enum tl =
- "<OL>\n"^
- (String.concat ""
- (List.map (fun t -> "<li>"^(self#html_of_text t)^"</li>\n") tl))^
- "</OL>\n"
-
- method html_of_Newline = "\n<p>\n"
-
- method html_of_Block t =
- "<blockquote>\n"^(self#html_of_text t)^"</blockquote>\n"
-
- method html_of_Title n label_opt t =
+ Format.fprintf fmt "@{<code class=\"%s\">%s@}" Odoc_ocamlhtml.code_class (self#escape s);
+ Format.fprintf fmt "@}"
+
+ method html_of_Verbatim fmt s = Format.fprintf fmt "@{<pre>%s@}" (self#escape s)
+
+ method html_of_Bold fmt t =
+ Format.fprintf fmt "@{<b>";
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}"
+
+ method html_of_Italic fmt t =
+ Format.fprintf fmt "@{<i>";
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}"
+
+ method html_of_Emphasize fmt t =
+ Format.fprintf fmt "@{<em>";
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}"
+
+ method html_of_Center fmt t =
+ Format.fprintf fmt "@{<center>";
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}"
+
+ method html_of_Left fmt t =
+ Format.fprintf fmt "@{<div align=left>";
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}"
+
+ method html_of_Right fmt t =
+ Format.fprintf fmt "@{<div align=right>";
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}"
+
+ method html_of_List fmt tl =
+ Format.fprintf fmt "@{<ul>";
+ List.iter
+ (fun t ->
+ Format.fprintf fmt "@{<li>" ;
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}")
+ tl;
+ Format.fprintf fmt "@}"
+
+ method html_of_Enum fmt tl =
+ Format.fprintf fmt "@{<ol>";
+ List.iter
+ (fun t ->
+ Format.fprintf fmt "@{<li>" ;
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}")
+ tl;
+ Format.fprintf fmt "@}"
+
+ method html_of_Newline fmt =
+ Format.pp_print_string fmt "\n<p>\n"
+
+ method html_of_Block fmt t =
+ Format.fprintf fmt "@{<blockquote>";
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}"
+
+ method html_of_Title fmt n label_opt t =
let css_class = "title"^(string_of_int n) in
- "<br>\n"^
+ Format.pp_print_string fmt "<br>\n";
(
match label_opt with
- None -> ""
- | Some l -> "<a name=\""^(Naming.label_target l)^"\"></a>"
- )^
- "<table cellpadding=0 cellspacing=0 width=\"100%\">\n"^
- "<tr class=\""^css_class^"\"><td><div align=center>\n"^
- "<table><tr class=\""^css_class^"\">\n"^
- "<td width=\"100%\" align=center>\n"^
- "<span class=\""^css_class^"\">"^(self#html_of_text t)^"</span>\n"^
- "</td>\n</tr>\n</table>\n</div>\n</td>\n</tr>\n</table>\n"
-
- method html_of_Latex _ = ""
+ None -> ()
+ | Some l -> Format.fprintf fmt "@{<mark \"%s\">@}" (Naming.label_target l)
+ );
+ Format.fprintf fmt "@{<table cellpadding=0 cellspacing=0 width=\"100%%\">";
+ Format.fprintf fmt "@{<tr class=\"%s\">@{<td>@{<div align=center>" css_class;
+ Format.fprintf fmt "@{<table>@{<tr class=\"%s\">\n" css_class;
+ Format.fprintf fmt "@{<td width=\"100%%\" align=center>";
+ Format.fprintf fmt "@{<span class=\"%s\">" css_class;
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}@}@}@}@}@}@}@}"
+
+ method html_of_Latex fmt _ = ()
(* don't care about LaTeX stuff in HTML. *)
- method html_of_Link s t =
- "<a href=\""^s^"\">"^(self#html_of_text t)^"</a>"
+ method html_of_Link fmt s t =
+ Format.fprintf fmt "@{<href \"%s\">" s;
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}"
- method html_of_Ref name ref_opt =
+ method html_of_Ref fmt name ref_opt =
match ref_opt with
None ->
- self#html_of_text_element (Odoc_info.Code name)
+ self#html_of_text_element fmt (Odoc_info.Code name)
| Some kind ->
let target =
match kind with
@@ -244,15 +288,19 @@ class text =
| Odoc_info.RK_method -> Naming.complete_target Naming.mark_method name
| Odoc_info.RK_section -> Naming.complete_label_target name
in
- "<a href=\""^target^"\">"^
- (self#html_of_text_element (Odoc_info.Code (Odoc_info.use_hidden_modules name)))^"</a>"
-
- method html_of_Superscript t =
- "<sup class=\"superscript\">"^(self#html_of_text t)^"</sup>"
-
- method html_of_Subscript t =
- "<sub class=\"subscript\">"^(self#html_of_text t)^"</sub>"
-
+ Format.fprintf fmt "@{<href \"%s\">" target;
+ self#html_of_text_element fmt (Odoc_info.Code (Odoc_info.use_hidden_modules name));
+ Format.fprintf fmt "@}"
+
+ method html_of_Superscript fmt t =
+ Format.fprintf fmt "@{<sup class=\"superscript\">";
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}"
+
+ method html_of_Subscript fmt t =
+ Format.fprintf fmt "@{<sup class=\"subscript\">";
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}"
end
(** A class used to generate html code for info structures. *)
@@ -261,138 +309,146 @@ class virtual info =
(** The list of pairs [(tag, f)] where [f] is a function taking
the [text] associated to [tag] and returning html code.
Add a pair here to handle a tag.*)
- val mutable tag_functions = ([] : (string * (Odoc_info.text -> string)) list)
+ val mutable tag_functions = ([] : (string * (Format.formatter -> Odoc_info.text -> unit)) list)
(** The method used to get html code from a [text]. *)
- method virtual html_of_text : Odoc_info.text -> string
+ method virtual html_of_text : Format.formatter -> Odoc_info.text -> unit
- (** Return html for an author list. *)
- method html_of_author_list l =
+ (** Print html for an author list. *)
+ method html_of_author_list fmt l =
match l with
- [] ->
- ""
- | _ ->
- "<b>"^Odoc_messages.authors^": </b>"^
- (String.concat ", " l)^
- "<br>\n"
+ [] -> ()
+ | _ -> Format.fprintf fmt "@{<b>%s: @}%s<br>\n"
+ Odoc_messages.authors (String.concat ", " l)
- (** Return html code for the given optional version information.*)
- method html_of_version_opt v_opt =
+ (** Print html code for the given optional version information.*)
+ method html_of_version_opt fmt v_opt =
match v_opt with
- None -> ""
- | Some v -> "<b>"^Odoc_messages.version^": </b>"^v^"<br>\n"
+ None -> ()
+ | Some v -> Format.fprintf fmt "@{<b>%s: @}%s<br>\n" Odoc_messages.version v
- (** Return html code for the given optional since information.*)
- method html_of_since_opt s_opt =
+ (** Print html code for the given optional since information.*)
+ method html_of_since_opt fmt s_opt =
match s_opt with
- None -> ""
- | Some s -> "<b>"^Odoc_messages.since^"</b> "^s^"<br>\n"
+ None -> ()
+ | Some s -> Format.fprintf fmt "@{<b>%s :@}%s<br>\n" Odoc_messages.since s
- (** Return html code for the given list of raised exceptions.*)
- method html_of_raised_exceptions l =
+ (** Print html code for the given list of raised exceptions.*)
+ method html_of_raised_exceptions fmt l =
match l with
- [] -> ""
- | (s, t) :: [] -> "<b>"^Odoc_messages.raises^"</b> <code>"^s^"</code> "^(self#html_of_text t)^"<br>\n"
+ [] -> ()
+ | (s, t) :: [] ->
+ Format.fprintf fmt "@{<b>%s@} @{<code>%s@} " Odoc_messages.raises s;
+ self#html_of_text fmt t;
+ Format.pp_print_string fmt "<br>\n"
| _ ->
- "<b>"^Odoc_messages.raises^"</b><ul>"^
- (String.concat ""
- (List.map
- (fun (ex, desc) -> "<li><code>"^ex^"</code> "^(self#html_of_text desc)^"</li>\n")
- l
- )
- )^"</ul>\n"
-
- (** Return html code for the given "see also" reference. *)
- method html_of_see (see_ref, t) =
+ Format.fprintf fmt "@{<b>%s@}@{<ul>" Odoc_messages.raises;
+ List.iter
+ (fun (ex, desc) ->
+ Format.fprintf fmt "@{<li>@{<code>%s@} " ex;
+ self#html_of_text fmt desc;
+ Format.fprintf fmt "@}"
+ )
+ l;
+ Format.fprintf fmt "@}"
+
+ (** Print html code for the given "see also" reference. *)
+ method html_of_see fmt (see_ref, t) =
let t_ref =
match see_ref with
Odoc_info.See_url s -> [ Odoc_info.Link (s, t) ]
| Odoc_info.See_file s -> (Odoc_info.Code s) :: (Odoc_info.Raw " ") :: t
| Odoc_info.See_doc s -> (Odoc_info.Italic [Odoc_info.Raw s]) :: (Odoc_info.Raw " ") :: t
in
- self#html_of_text t_ref
+ self#html_of_text fmt t_ref
- (** Return html code for the given list of "see also" references.*)
- method html_of_sees l =
+ (** Print html code for the given list of "see also" references.*)
+ method html_of_sees fmt l =
match l with
- [] -> ""
- | see :: [] -> "<b>"^Odoc_messages.see_also^"</b> "^(self#html_of_see see)^"<br>\n"
+ [] -> ()
+ | see :: [] ->
+ Format.fprintf fmt "@{<b>%s@} " Odoc_messages.see_also;
+ self#html_of_see fmt see;
+ Format.pp_print_string fmt "<br>\n"
| _ ->
- "<b>"^Odoc_messages.see_also^"</b><ul>"^
- (String.concat ""
- (List.map
- (fun see -> "<li>"^(self#html_of_see see)^"</li>\n")
- l
- )
- )^"</ul>\n"
-
- (** Return html code for the given optional return information.*)
- method html_of_return_opt return_opt =
+ Format.fprintf fmt "@{<b>%s@}@{<ul>" Odoc_messages.see_also;
+ List.iter
+ (fun see ->
+ Format.fprintf fmt "@{<li>";
+ self#html_of_see fmt see;
+ Format.fprintf fmt "@}"
+ )
+ l;
+ Format.fprintf fmt "@}"
+
+ (** Print html code for the given optional return information.*)
+ method html_of_return_opt fmt return_opt =
match return_opt with
- None -> ""
- | Some s -> "<b>"^Odoc_messages.returns^"</b> "^(self#html_of_text s)^"<br>\n"
+ None -> ()
+ | Some s ->
+ Format.fprintf fmt "@{<b>%s@} " Odoc_messages.returns;
+ self#html_of_text fmt s;
+ Format.pp_print_string fmt "<br>\n"
- (** Return html code for the given list of custom tagged texts. *)
- method html_of_custom l =
+ (** Print html code for the given list of custom tagged texts. *)
+ method html_of_custom fmt l =
let buf = Buffer.create 50 in
List.iter
(fun (tag, text) ->
try
let f = List.assoc tag tag_functions in
- Buffer.add_string buf (f text)
+ f fmt text
with
Not_found ->
Odoc_info.warning (Odoc_messages.tag_not_handled tag)
)
- l;
- Buffer.contents buf
+ l
- (** Return html code for a description, except for the [i_params] field. *)
- method html_of_info info_opt =
+ (** Print html code for a description, except for the [i_params] field. *)
+ method html_of_info fmt info_opt =
match info_opt with
- None ->
- ""
+ None -> ()
| Some info ->
let module M = Odoc_info in
- "<div class=\"info\">\n"^
+ Format.fprintf fmt "@{<div class=\"info\">\n";
(match info.M.i_deprecated with
- None -> ""
+ None -> ()
| Some d ->
- "<span class=\"warning\">"^Odoc_messages.deprecated^"</span> "^
- (self#html_of_text d)^
- "<br>\n"
- )^
+ Format.fprintf fmt "@{<span class=\"warning\">%s@} " Odoc_messages.deprecated;
+ self#html_of_text fmt d;
+ Format.pp_print_string fmt "<br>\n"
+ );
(match info.M.i_desc with
- None -> ""
- | Some d when d = [Odoc_info.Raw ""] -> ""
- | Some d -> (self#html_of_text d)^"<br>\n"
- )^
- (self#html_of_author_list info.M.i_authors)^
- (self#html_of_version_opt info.M.i_version)^
- (self#html_of_since_opt info.M.i_since)^
- (self#html_of_raised_exceptions info.M.i_raised_exceptions)^
- (self#html_of_return_opt info.M.i_return_value)^
- (self#html_of_sees info.M.i_sees)^
- (self#html_of_custom info.M.i_custom)^
- "</div>\n"
-
- (** Return html code for the first sentence of a description. *)
- method html_of_info_first_sentence info_opt =
+ None -> ()
+ | Some d when d = [Odoc_info.Raw ""] -> ()
+ | Some d -> self#html_of_text fmt d; Format.pp_print_string fmt "<br>\n"
+ );
+ self#html_of_author_list fmt info.M.i_authors;
+ self#html_of_version_opt fmt info.M.i_version;
+ self#html_of_since_opt fmt info.M.i_since;
+ self#html_of_raised_exceptions fmt info.M.i_raised_exceptions;
+ self#html_of_return_opt fmt info.M.i_return_value;
+ self#html_of_sees fmt info.M.i_sees;
+ self#html_of_custom fmt info.M.i_custom;
+ Format.fprintf fmt "@}\n"
+
+ (** Print html code for the first sentence of a description. *)
+ method html_of_info_first_sentence fmt info_opt =
match info_opt with
- None -> ""
+ None -> ()
| Some info ->
let module M = Odoc_info in
let dep = info.M.i_deprecated <> None in
- "<div class=\"info\">\n"^
- (if dep then "<font color=\"#CCCCCC\">" else "") ^
+ Format.fprintf fmt "@{<div class=\"info\">";
+ if dep then Format.fprintf fmt "@{<font color=\"#CCCCCC\">";
(match info.M.i_desc with
- None -> ""
- | Some d when d = [Odoc_info.Raw ""] -> ""
- | Some d -> (self#html_of_text (Odoc_info.first_sentence_of_text d))^"\n"
- )^
- (if dep then "</font>" else "") ^
- "</div>\n"
-
+ None -> ()
+ | Some d when d = [Odoc_info.Raw ""] -> ()
+ | Some d ->
+ self#html_of_text fmt (Odoc_info.first_sentence_of_text d)
+ );
+ if dep then Format.fprintf fmt "@}";
+ Format.fprintf fmt "@}"
end
@@ -417,6 +473,7 @@ class html =
".subscript { font-size : 4 }" ;
".comment { color : Green }" ;
".constructor { color : Blue }" ;
+ ".type { color : DarkSlateBlue }" ;
".string { color : Maroon }" ;
".warning { color : Red ; font-weight : bold }" ;
".info { margin-left : 3em; margin-right : 3em }" ;
@@ -494,7 +551,7 @@ class html =
val mutable list_class_types = []
(** The header of pages. Must be prepared by the [prepare_header] method.*)
- val mutable header = fun ?(nav=None) -> fun _ -> ""
+ val mutable header = fun fmt -> fun ?(nav=None) -> fun _ -> ()
(** Init the style. *)
method init_style =
@@ -515,7 +572,7 @@ class html =
| Some f ->
style_file <- f
);
- style <- "<link rel=\"stylesheet\" href=\""^style_file^"\" type=\"text/css\">\n"
+ style <- "<link rel=\"stylesheet\" href=\""^style_file^"\" type=\"text/css\">"
(** Get the title given by the user *)
method title = match !Odoc_args.title with None -> "" | Some t -> self#escape t
@@ -526,103 +583,101 @@ class html =
(self#escape s)
(** Get the page header. *)
- method header ?nav title = header ?nav title
+ method header fmt ?nav title = header fmt ?nav title
(** A function to build the header of pages. *)
method prepare_header module_list =
- let f ?(nav=None) t =
+ let f fmt ?(nav=None) t =
let link_if_not_empty l m url =
match l with
- [] -> ""
- | _ -> "<link title=\""^m^"\" rel=Appendix href=\""^url^"\">\n"
+ [] -> ()
+ | _ -> Format.fprintf fmt "<link title=\"%s\" rel=Appendix href=\"%s\">\n" m url
in
- "<head>\n"^
- style^
- "<link rel=\"Start\" href=\""^index^"\">\n"^
+ Format.fprintf fmt "@{<head>%s\n" style;
+ Format.fprintf fmt "<link rel=\"Start\" href=\"%s\">\n" index;
(
match nav with
- None -> ""
+ None -> ()
| Some (pre_opt, post_opt, name) ->
(match pre_opt with
- None -> ""
+ None -> ()
| Some name ->
- "<link rel=\"previous\" href=\""^(fst (Naming.html_files name))^"\">\n"
- )^
+ Format.fprintf fmt "<link rel=\"previous\" href=\"%s\">\n"
+ (fst (Naming.html_files name))
+ );
(match post_opt with
- None -> ""
+ None -> ()
| Some name ->
- "<link rel=\"next\" href=\""^(fst (Naming.html_files name))^"\">\n"
- )^
- (
- let father = Name.father name in
- let href = if father = "" then index else fst (Naming.html_files father) in
- "<link rel=\"Up\" href=\""^href^"\">\n"
- )
- )^
- (link_if_not_empty list_types Odoc_messages.index_of_types index_types)^
- (link_if_not_empty list_exceptions Odoc_messages.index_of_exceptions index_exceptions)^
- (link_if_not_empty list_values Odoc_messages.index_of_values index_values)^
- (link_if_not_empty list_attributes Odoc_messages.index_of_attributes index_attributes)^
- (link_if_not_empty list_methods Odoc_messages.index_of_methods index_methods)^
- (link_if_not_empty list_classes Odoc_messages.index_of_classes index_classes)^
- (link_if_not_empty list_class_types Odoc_messages.index_of_class_types index_class_types)^
- (link_if_not_empty list_modules Odoc_messages.index_of_modules index_modules)^
- (link_if_not_empty list_module_types Odoc_messages.index_of_module_types index_module_types)^
- (String.concat "\n"
- (List.map
- (fun m ->
- let html_file = fst (Naming.html_files m.m_name) in
- "<link title=\""^m.m_name^"\" rel=\"Chapter\" href=\""^html_file^"\">\n"
- )
- module_list
- )
- )^
- "<title>"^
- t^
- "</title>\n</head>\n"
+ Format.fprintf fmt "<link rel=\"next\" href=\"%s\">\n"
+ (fst (Naming.html_files name))
+ );
+ let father = Name.father name in
+ let href = if father = "" then index else fst (Naming.html_files father) in
+ Format.fprintf fmt "<link rel=\"Up\" href=\"%s\">\n" href
+ );
+ link_if_not_empty list_types Odoc_messages.index_of_types index_types;
+ link_if_not_empty list_exceptions Odoc_messages.index_of_exceptions index_exceptions;
+ link_if_not_empty list_values Odoc_messages.index_of_values index_values;
+ link_if_not_empty list_attributes Odoc_messages.index_of_attributes index_attributes;
+ link_if_not_empty list_methods Odoc_messages.index_of_methods index_methods;
+ link_if_not_empty list_classes Odoc_messages.index_of_classes index_classes;
+ link_if_not_empty list_class_types Odoc_messages.index_of_class_types index_class_types;
+ link_if_not_empty list_modules Odoc_messages.index_of_modules index_modules;
+ link_if_not_empty list_module_types Odoc_messages.index_of_module_types index_module_types;
+ List.iter
+ (fun m ->
+ let html_file = fst (Naming.html_files m.m_name) in
+ Format.fprintf fmt
+ "<link title=\"%s\" rel=\"Chapter\" href=\"%s\">\n"
+ m.m_name html_file
+ )
+ module_list;
+ Format.fprintf fmt "@{<title>%s@}@}" t
in
header <- f
- (** Html code for navigation bar.
+ (** Print HTML code for navigation bar.
@param pre optional name for optional previous module/class
@param post optional name for optional next module/class
@param name name of current module/class *)
- method navbar pre post name =
- "<div class=\"navbar\">"^
+ method navbar fmt pre post name =
+ Format.fprintf fmt "@{<div class=\"navbar\">";
(match pre with
- None -> ""
+ None -> ()
| Some name ->
- "<a href=\""^(fst (Naming.html_files name))^"\">"^Odoc_messages.previous^"</a>\n"
- )^
- "&nbsp;"^
- (
- let father = Name.father name in
- let href = if father = "" then index else fst (Naming.html_files father) in
- "<a href=\""^href^"\">"^Odoc_messages.up^"</a>\n"
- )^
- "&nbsp;"^
+ Format.fprintf fmt "@{<href \"%s\">%s@}\n"
+ (fst (Naming.html_files name))
+ Odoc_messages.previous
+ );
+ let father = Name.father name in
+ let href = if father = "" then index else fst (Naming.html_files father) in
+ Format.fprintf fmt "&nbsp;@{<href \"%s\">%s@}\n&nbsp;" href Odoc_messages.up;
+
(match post with
- None -> ""
- | Some name ->
- "<a href=\""^(fst (Naming.html_files name))^"\">"^Odoc_messages.next^"</a>\n"
- )^
- "</div>\n"
+ None -> ()
+ | Some name -> Format.fprintf fmt "@{<href \"%s\">%s@}\n"
+ (fst (Naming.html_files name)) Odoc_messages.next
+ );
+ Format.fprintf fmt "@}"
- (** Return html code with the given string in the keyword style.*)
- method keyword s =
- "<span class=\"keyword\">"^s^"</span>"
+ (** Print html code with the given string in the keyword style.*)
+ method keyword fmt s =
+ Format.fprintf fmt "@{<span class=\"keyword\">%s@}" s
- (** Return html code with the given string in the constructor style. *)
- method constructor s = "<span class=\"constructor\">"^s^"</span>"
+ (** Print html code with the given string in the constructor style. *)
+ method constructor fmt s =
+ Format.fprintf fmt "@{<span class=\"constructor\">%s@}" s
(** Output the given ocaml code to the given file name. *)
method private output_code in_title file code =
try
- let chanout = open_out file in
- let html_code = self#html_of_code code in
- output_string chanout ("<html>"^(self#header (self#inner_title in_title))^"<body>\n");
- output_string chanout html_code;
- output_string chanout "</body></html>";
+ let (fmt, chanout) = self#formatter_of_file file in
+ Format.fprintf fmt "@{<html>";
+ self#header fmt (self#inner_title in_title);
+ Format.fprintf fmt "@{<body>";
+ self#html_of_code fmt code;
+ Format.fprintf fmt "@}@}";
+ Format.pp_print_flush fmt ();
close_out chanout
with
Sys_error s ->
@@ -677,40 +732,43 @@ class html =
in
s2
- (** Return html code to display a [Types.type_expr].*)
- method html_of_type_expr m_name t =
+ (** Print html code to display a [Types.type_expr].*)
+ method html_of_type_expr fmt m_name t =
let s = String.concat "\n"
(Str.split (Str.regexp "\n") (Odoc_info.string_of_type_expr t))
in
let s2 = Str.global_replace (Str.regexp "\n") "<br> " s in
- "<code class=\"type\">"^(self#create_fully_qualified_idents_links m_name s2)^"</code>"
-
+ Format.fprintf fmt "@{<code class=\"type\">%s@}"
+ (self#create_fully_qualified_idents_links m_name s2)
- (** Return html code to display a [Types.class_type].*)
- method html_of_class_type_expr m_name t =
+ (** Print html code to display a [Types.class_type].*)
+ method html_of_class_type_expr fmt m_name t =
let s = String.concat "\n"
(Str.split (Str.regexp "\n") (Odoc_info.string_of_class_type t))
in
let s2 = Str.global_replace (Str.regexp "\n") "<br> " s in
- "<code class=\"type\">"^(self#create_fully_qualified_idents_links m_name s2)^"</code>"
+ Format.fprintf fmt "@{<code class=\"type\">%s@}"
+ (self#create_fully_qualified_idents_links m_name s2)
- (** Return html code to display a [Types.type_expr list].*)
- method html_of_type_expr_list m_name sep l =
+ (** Print html code to display a [Types.type_expr list].*)
+ method html_of_type_expr_list fmt m_name sep l =
print_DEBUG "html#html_of_type_expr_list";
let s = Odoc_info.string_of_type_list sep l in
print_DEBUG "html#html_of_type_expr_list: 1";
let s2 = Str.global_replace (Str.regexp "\n") "<br> " s in
print_DEBUG "html#html_of_type_expr_list: 2";
- "<code class=\"type\">"^(self#create_fully_qualified_idents_links m_name s2)^"</code>"
+ Format.fprintf fmt "@{<code class=\"type\">%s@}"
+ (self#create_fully_qualified_idents_links m_name s2)
- (** Return html code to display a [Types.module_type]. *)
- method html_of_module_type m_name t =
+ (** Print html code to display a [Types.module_type]. *)
+ method html_of_module_type fmt m_name t =
let s = String.concat "\n"
(Str.split (Str.regexp "\n") (Odoc_info.string_of_module_type t))
in
let s2 = Str.global_replace (Str.regexp "\n") "<br> " s in
- "<code class=\"type\">"^(self#create_fully_qualified_module_idents_links m_name s2)^"</code>"
-
+ Format.fprintf fmt "@{<code class=\"type\">%s@}"
+ (self#create_fully_qualified_module_idents_links m_name s2)
+
(** Generate a file containing the module type in the given file name. *)
method output_module_type in_title file mtyp =
let s = String.concat "\n"
@@ -726,253 +784,256 @@ class html =
self#output_code in_title file s
- (** Return html code for a value. *)
- method html_of_value v =
+ (** Print html code for a value. *)
+ method html_of_value fmt v =
Odoc_info.reset_type_names ();
- "<pre>"^(self#keyword "val")^" "^
+ Format.fprintf fmt "@{<pre>";
+ self#keyword fmt "val";
(* html mark *)
- "<a name=\""^(Naming.value_target v)^"\"></a>"^
+ Format.fprintf fmt " @{<mark \"%s\">@}" (Naming.value_target v);
(match v.val_code with
- None -> Name.simple v.val_name
+ None -> Format.fprintf fmt "%s" (Name.simple v.val_name)
| Some c ->
let file = Naming.file_code_value_complete_target v in
self#output_code v.val_name (Filename.concat !Odoc_args.target_dir file) c;
- "<a href=\""^file^"\">"^(Name.simple v.val_name)^"</a>"
- )^" : "^
- (self#html_of_type_expr (Name.father v.val_name) v.val_type)^"</pre>"^
- (self#html_of_info v.val_info)^
- (if !Odoc_args.with_parameter_list then
- self#html_of_parameter_list (Name.father v.val_name) v.val_parameters
+ Format.fprintf fmt "@{<href \"%s\">%s@}" file (Name.simple v.val_name)
+ );
+ Format.pp_print_string fmt " : ";
+ self#html_of_type_expr fmt (Name.father v.val_name) v.val_type;
+ Format.fprintf fmt "@}";
+ self#html_of_info fmt v.val_info;
+
+ if !Odoc_args.with_parameter_list then
+ self#html_of_parameter_list fmt (Name.father v.val_name) v.val_parameters
else
- self#html_of_described_parameter_list (Name.father v.val_name) v.val_parameters
- )
+ self#html_of_described_parameter_list fmt (Name.father v.val_name) v.val_parameters
- (** Return html code for an exception. *)
- method html_of_exception e =
+ (** Print html code for an exception. *)
+ method html_of_exception fmt e =
Odoc_info.reset_type_names ();
- "<pre>"^(self#keyword "exception")^" "^
+ Format.fprintf fmt "@{<pre>";
+ self#keyword fmt "exception";
(* html mark *)
- "<a name=\""^(Naming.exception_target e)^"\"></a>"^
- (Name.simple e.ex_name)^
+ Format.fprintf fmt " @{<mark \"%s\">@}" (Naming.exception_target e);
+ Format.pp_print_string fmt (Name.simple e.ex_name);
(match e.ex_args with
- [] -> ""
+ [] -> ()
| _ ->
- " "^(self#keyword "of")^" "^
- (self#html_of_type_expr_list (Name.father e.ex_name) " * " e.ex_args)
- )^
+ Format.pp_print_string fmt " ";
+ self#keyword fmt "of";
+ Format.pp_print_string fmt " ";
+ self#html_of_type_expr_list fmt (Name.father e.ex_name) " * " e.ex_args
+ );
(match e.ex_alias with
- None -> ""
- | Some ea -> " = "^
+ None -> ()
+ | Some ea ->
+ Format.pp_print_string fmt " = ";
(
match ea.ea_ex with
- None -> ea.ea_name
- | Some e -> "<a href=\""^(Naming.complete_exception_target e)^"\">"^e.ex_name^"</a>"
+ None -> Format.pp_print_string fmt ea.ea_name
+ | Some e -> Format.fprintf fmt "@{<href \"%s\">%s@}" (Naming.complete_exception_target e) e.ex_name
)
- )^
- "</pre>\n"^
- (self#html_of_info e.ex_info)
+ );
+ Format.fprintf fmt "@}";
+ self#html_of_info fmt e.ex_info
- (** Return html code for a type. *)
- method html_of_type t =
+ (** Print html code for a type. *)
+ method html_of_type fmt t =
Odoc_info.reset_type_names ();
let father = Name.father t.ty_name in
- "<br><code>"^(self#keyword "type")^" "^
+ Format.fprintf fmt "<br>@{<code>";
+ self#keyword fmt "type";
(* html mark *)
- "<a name=\""^(Naming.type_target t)^"\"></a>"^
+ Format.fprintf fmt " <mark \"%s\">" (Naming.type_target t);
(match t.ty_parameters with
- [] -> ""
- | tp :: [] -> (self#html_of_type_expr father tp)^" "
- | l -> "("^(self#html_of_type_expr_list father ", " l)^") "
- )^
- (Name.simple t.ty_name)^" "^
- (match t.ty_manifest with None -> "" | Some typ -> "= "^(self#html_of_type_expr father typ)^" ")^
+ [] -> ()
+ | tp :: [] -> self#html_of_type_expr fmt father tp; Format.pp_print_string fmt " "
+ | l ->
+ Format.pp_print_string fmt "(";
+ self#html_of_type_expr_list fmt father ", " l;
+ Format.pp_print_string fmt ") "
+ );
+ Format.fprintf fmt "%s " (Name.simple t.ty_name);
+ (match t.ty_manifest with
+ None -> ()
+ | Some typ -> Format.pp_print_string fmt "= ";
+ self#html_of_type_expr fmt father typ;
+ Format.pp_print_string fmt " "
+ );
(match t.ty_kind with
- Type_abstract -> "</code>"
+ Type_abstract -> Format.fprintf fmt "@}"
| Type_variant l ->
- "=<br>"^
- "</code><table border=\"0\" cellpadding=\"1\">\n"^
- (String.concat "\n"
- (List.map
- (fun constr ->
- "<tr>\n"^
- "<td align=\"left\" valign=\"top\" >\n"^
- "<code>"^
- (self#keyword "|")^
- "</code></td>\n"^
- "<td align=\"left\" valign=\"top\" >\n"^
- "<code>"^
- (self#constructor constr.vc_name)^
- (match constr.vc_args with
- [] -> ""
- | l ->
- " "^(self#keyword "of")^" "^
- (self#html_of_type_expr_list father " * " l)
- )^
- "</code></td>\n"^
- (match constr.vc_text with
- None -> ""
- | Some t ->
- "<td align=\"left\" valign=\"top\" >"^
- "<code>"^
- "(*"^
- "</code></td>"^
- "<td align=\"left\" valign=\"top\" >"^
- "<code>"^
- (self#html_of_text t)^
- "</code></td>"^
- "<td align=\"left\" valign=\"bottom\" >"^
- "<code>"^
- "*)"^
- "</code></td>"
- )^
- "\n</tr>"
- )
- l
- )
- )^
- "</table>\n"
+ Format.fprintf fmt "=<br>@}@{<table border=\"0\" cellpadding=\"1\">";
+ List.iter
+ (fun constr ->
+ Format.fprintf fmt "@{<tr>@{<td align=\"left\" valign=\"top\">@{<code>";
+ self#keyword fmt "|";
+ Format.fprintf fmt "@}@}@{<td align=\"left\" valign=\"top\">@{<code>";
+ self#constructor fmt constr.vc_name;
+ (match constr.vc_args with
+ [] -> ()
+ | l ->
+ Format.pp_print_string fmt " ";
+ self#keyword fmt "of";
+ Format.pp_print_string fmt " ";
+ self#html_of_type_expr_list fmt father " * " l
+ );
+ Format.fprintf fmt "@}@}";
+ (
+ match constr.vc_text with
+ None -> ()
+ | Some t ->
+ Format.fprintf fmt "@{<td align=\"left\" valign=\"top\">@{<code>";
+ Format.fprintf fmt "(*@}@}@{<td align=\"left\" valign=\"top\">@{<code>";
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}@}@{<td align=\"left\" valign=\"bottom\">@{<code>*)@}@}"
+ );
+ Format.fprintf fmt "@}"
+ )
+ l;
+ Format.fprintf fmt "@}\n"
| Type_record l ->
- "= {<br>"^
- "</code><table border=\"0\" cellpadding=\"1\">\n"^
- (String.concat "\n"
- (List.map
- (fun r ->
- "<tr>\n"^
- "<td align=\"left\" valign=\"top\" >\n"^
- "<code>&nbsp;&nbsp;</code>"^
- "</td>\n"^
- "<td align=\"left\" valign=\"top\" >\n"^
- "<code>"^(if r.rf_mutable then self#keyword "mutable&nbsp;" else "")^
- r.rf_name^"&nbsp;: "^(self#html_of_type_expr father r.rf_type)^";"^
- "</code></td>\n"^
- (match r.rf_text with
- None -> ""
- | Some t ->
- "<td align=\"left\" valign=\"top\" >"^
- "<code>"^
- "(*"^
- "</code></td>"^
- "<td align=\"left\" valign=\"top\" >"^
- "<code>"^
- (self#html_of_text t)^
- "</code></td>"^
- "<td align=\"left\" valign=\"bottom\" >"^
- "<code>"^
- "*)"^
- "</code></td>"
- )^
- "\n</tr>"
- )
- l
- )
- )^
- "</table>\n"^
- "}\n"
- )^"\n"^
- (self#html_of_info t.ty_info)^
- "<br>\n"
-
- (** Return html code for a class attribute. *)
- method html_of_attribute a =
+ Format.fprintf fmt "= {<br>@}@{<table border=\"0\" cellpadding=\"1\">";
+ List.iter
+ (fun r ->
+ Format.fprintf fmt "@{<tr>@{<td align=\"left\" valign=\"top\">@{<code>&nbsp;&nbsp;@}";
+ Format.fprintf fmt "@}@{<td align=\"left\" valign=\"top\" >@{<code>";
+ if r.rf_mutable then self#keyword fmt "mutable&nbsp;";
+ Format.fprintf fmt "%s&nbsp;: " r.rf_name;
+ self#html_of_type_expr fmt father r.rf_type;
+ Format.fprintf fmt ";@}@}";
+ (
+ match r.rf_text with
+ None -> ()
+ | Some t ->
+ Format.fprintf fmt "@{<td align=\"left\" valign=\"top\">@{<code>(*@}@}";
+ Format.fprintf fmt "@{<td align=\"left\" valign=\"top\">@{<code>";
+ self#html_of_text fmt t;
+ Format.fprintf fmt "@}@}@{<td align=\"left\" valign=\"bottom\">@{<code>*)@}@}"
+ );
+ Format.fprintf fmt "@}"
+ )
+ l;
+ Format.fprintf fmt "@}}\n"
+ );
+ self#html_of_info fmt t.ty_info;
+ Format.pp_print_string fmt "<br>\n"
+
+ (** Print html code for a class attribute. *)
+ method html_of_attribute fmt a =
let module_name = Name.father (Name.father a.att_value.val_name) in
- "<pre>"^(self#keyword "val")^" "^
+ Format.fprintf fmt "@{<pre>";
+ self#keyword fmt "val";
(* html mark *)
- "<a name=\""^(Naming.attribute_target a)^"\"></a>"^
- (if a.att_mutable then (self#keyword Odoc_messages.mutab)^" " else "")^
+ Format.fprintf fmt " @{<mark \"%s\">@}" (Naming.attribute_target a);
+
+ if a.att_mutable then
+ (
+ self#keyword fmt Odoc_messages.mutab;
+ Format.pp_print_string fmt " "
+ );
(match a.att_value.val_code with
- None -> Name.simple a.att_value.val_name
+ None -> Format.pp_print_string fmt (Name.simple a.att_value.val_name)
| Some c ->
let file = Naming.file_code_attribute_complete_target a in
self#output_code a.att_value.val_name (Filename.concat !Odoc_args.target_dir file) c;
- "<a href=\""^file^"\">"^(Name.simple a.att_value.val_name)^"</a>"
- )^" : "^
- (self#html_of_type_expr module_name a.att_value.val_type)^"</pre>"^
- (self#html_of_info a.att_value.val_info)
+ Format.fprintf fmt "@{<href \"%s\">%s@}" file (Name.simple a.att_value.val_name)
+ );
+ Format.pp_print_string fmt " : ";
+ self#html_of_type_expr fmt module_name a.att_value.val_type;
+ Format.fprintf fmt "@}";
+ self#html_of_info fmt a.att_value.val_info
- (** Return html code for a class method. *)
- method html_of_method m =
+ (** Print html code for a class method. *)
+ method html_of_method fmt m =
let module_name = Name.father (Name.father m.met_value.val_name) in
- "<pre>"^(self#keyword "method")^" "^
+ Format.fprintf fmt "@{<pre>";
+ self#keyword fmt "method" ;
(* html mark *)
- "<a name=\""^(Naming.method_target m)^"\"></a>"^
- (if m.met_private then (self#keyword "private")^" " else "")^
- (if m.met_virtual then (self#keyword "virtual")^" " else "")^
+ Format.fprintf fmt " @{<mark \"%s\">@}" (Naming.method_target m);
+ if m.met_private then
+ (
+ self#keyword fmt "private";
+ Format.pp_print_string fmt " ";
+ );
+ if m.met_virtual then
+ (
+ self#keyword fmt "virtual";
+ Format.pp_print_string fmt " ";
+ );
(match m.met_value.val_code with
- None -> Name.simple m.met_value.val_name
+ None -> Format.pp_print_string fmt (Name.simple m.met_value.val_name)
| Some c ->
let file = Naming.file_code_method_complete_target m in
self#output_code m.met_value.val_name (Filename.concat !Odoc_args.target_dir file) c;
- "<a href=\""^file^"\">"^(Name.simple m.met_value.val_name)^"</a>"
- )^" : "^
- (self#html_of_type_expr module_name m.met_value.val_type)^"</pre>"^
- (self#html_of_info m.met_value.val_info)^
+ Format.fprintf fmt "@{<href \"%s\">%s@}" file (Name.simple m.met_value.val_name)
+ );
+ Format.pp_print_string fmt " : ";
+ self#html_of_type_expr fmt module_name m.met_value.val_type;
+ Format.fprintf fmt "@}";
+ self#html_of_info fmt m.met_value.val_info;
(if !Odoc_args.with_parameter_list then
- self#html_of_parameter_list module_name m.met_value.val_parameters
+ self#html_of_parameter_list fmt module_name m.met_value.val_parameters
else
- self#html_of_described_parameter_list module_name m.met_value.val_parameters
+ self#html_of_described_parameter_list fmt module_name m.met_value.val_parameters
)
- (** Return html code for the description of a function parameter. *)
- method html_of_parameter_description p =
+ (** Print html code for the description of a function parameter. *)
+ method html_of_parameter_description fmt p =
match Parameter.names p with
- [] ->
- ""
+ [] -> ()
| name :: [] ->
(
(* Only one name, no need for label for the description. *)
match Parameter.desc_by_name p name with
- None -> ""
- | Some t -> self#html_of_text t
+ None -> ()
+ | Some t -> self#html_of_text fmt t
)
| l ->
(* A list of names, we display those with a description. *)
let l2 = List.filter (fun n -> (Parameter.desc_by_name p n) <> None) l in
- String.concat "<br>\n"
- (List.map
- (fun n ->
- match Parameter.desc_by_name p n with
- None -> ""
- | Some t -> "<code>"^n^"</code> : "^(self#html_of_text t)
- )
- l2
+ List.iter
+ (fun n ->
+ match Parameter.desc_by_name p n with
+ None -> ()
+ | Some t ->
+ Format.fprintf fmt "@{<code>%s@} : " n ;
+ self#html_of_text fmt t;
+ Format.pp_print_string fmt "<br>\n"
)
+ l2
- (** Return html code for a list of parameters. *)
- method html_of_parameter_list m_name l =
+ (** Print html code for a list of parameters. *)
+ method html_of_parameter_list fmt m_name l =
match l with
- [] ->
- ""
+ [] -> ()
| _ ->
- "<div class=\"info\">"^
- "<table border=\"0\" cellpadding=\"3\" width=\"100%\">\n"^
- "<tr>\n"^
- "<td align=\"left\" valign=\"top\" width=\"1%\"><b>"^Odoc_messages.parameters^": </b></td>\n"^
- "<td>\n"^
- "<table border=\"0\" cellpadding=\"5\" cellspacing=\"0\">\n"^
- (String.concat ""
- (List.map
- (fun p ->
- "<tr>\n"^
- "<td align=\"center\" valign=\"top\" width=\"15%\" class=\"code\">\n"^
- (match Parameter.complete_name p with
- "" -> "?"
- | s -> s
- )^"</td>\n"^
- "<td align=\"center\" valign=\"top\">:</td>\n"^
- "<td>"^(self#html_of_type_expr m_name (Parameter.typ p))^"<br>\n"^
- (self#html_of_parameter_description p)^"\n"^
- "</tr>\n"
- )
- l
- )
- )^"</table>\n"^
- "</td>\n"^
- "</tr>\n"^
- "</table></div>\n"
-
- (** Return html code for the parameters which have a name and description. *)
- method html_of_described_parameter_list m_name l =
+ Format.fprintf fmt "@{<div class=\"info\">";
+ Format.fprintf fmt "@{<table border=\"0\" cellpadding=\"3\" width=\"100%%\">\n@{<tr>";
+ Format.fprintf fmt
+ "@{<td align=\"left\" valign=\"top\" width=\"1%%\">@{<b>%s: @}@}"
+ Odoc_messages.parameters;
+ Format.fprintf fmt "@{<td>@{<table border=\"0\" cellpadding=\"5\" cellspacing=\"0\">";
+ List.iter
+ (fun p ->
+ Format.fprintf fmt
+ "@{<tr>@{<td align=\"center\" valign=\"top\" width=\"15%%\" class=\"code\">%s@}"
+ (match Parameter.complete_name p with
+ "" -> "?"
+ | s -> s);
+ Format.fprintf fmt "@{<td align=\"center\" valign=\"top\">:@}@{<td>";
+ self#html_of_type_expr fmt m_name (Parameter.typ p);
+ Format.pp_print_string fmt "<br>\n";
+ self#html_of_parameter_description fmt p;
+ Format.fprintf fmt "@}@}"
+ )
+ l;
+
+ Format.fprintf fmt "@}@}@}@}@}"
+
+ (** Print html code for the parameters which have a name and description. *)
+ method html_of_described_parameter_list fmt m_name l =
(* get the params which have a name, and at least one name described. *)
let l2 = List.filter
(fun p ->
@@ -982,96 +1043,89 @@ class html =
l
in
let f p =
- "<div class=\"info\"><code class=\"code\">"^(Parameter.complete_name p)^"</code> : "^
- (self#html_of_parameter_description p)^"</div>\n"
+ Format.fprintf fmt "@{<div class=\"info\">@{<code class=\"code\">%s@} : " (Parameter.complete_name p);
+ self#html_of_parameter_description fmt p;
+ Format.fprintf fmt "@}"
in
match l2 with
- [] -> ""
- | _ -> "<br>"^(String.concat "" (List.map f l2))
+ [] -> ()
+ | _ -> Format.fprintf fmt "<br>"; List.iter f l2
(** Return html code for a list of module parameters. *)
- method html_of_module_parameter_list m_name l =
+ method html_of_module_parameter_list fmt m_name l =
match l with
- [] ->
- ""
+ [] -> ()
| _ ->
- "<table border=\"0\" cellpadding=\"3\" width=\"100%\">\n"^
- "<tr>\n"^
- "<td align=\"left\" valign=\"top\" width=\"1%\"><b>"^Odoc_messages.parameters^": </b></td>\n"^
- "<td>\n"^
- "<table border=\"0\" cellpadding=\"5\" cellspacing=\"0\">\n"^
- (String.concat ""
- (List.map
- (fun (p, desc_opt) ->
- "<tr>\n"^
- "<td align=\"center\" valign=\"top\" width=\"15%\">\n"^
- "<code>"^p.mp_name^"</code></td>\n"^
- "<td align=\"center\" valign=\"top\">:</td>\n"^
- "<td>"^(self#html_of_module_type m_name p.mp_type)^"\n"^
- (match desc_opt with
- None -> ""
- | Some t -> "<br>"^(self#html_of_text t))^
- "\n"^
- "</tr>\n"
- )
- l
- )
- )^"</table>\n"^
- "</td>\n"^
- "</tr>\n"^
- "</table>\n"
-
- (** Return html code for a module. *)
- method html_of_module ?(info=true) ?(complete=true) ?(with_link=true) m =
+ Format.fprintf fmt "@{<table border=\"0\" cellpadding=\"3\" width=\"100%%\">@{<tr>";
+ Format.fprintf fmt "@{<td align=\"left\" valign=\"top\" width=\"1%%\">@{<b>%s: @}@}" Odoc_messages.parameters;
+ Format.fprintf fmt "@{<td>@{<table border=\"0\" cellpadding=\"5\" cellspacing=\"0\">";
+ List.iter
+ (fun (p, desc_opt) ->
+ Format.fprintf fmt "@{<tr>@{<td align=\"center\" valign=\"top\" width=\"15%%\">@{<code>%s@}@}" p.mp_name;
+ Format.fprintf fmt "@{<td align=\"center\" valign=\"top\">:@}@{<td>";
+ self#html_of_module_type fmt m_name p.mp_type;
+ (match desc_opt with
+ None -> ()
+ | Some t -> Format.pp_print_string fmt "<br>\n"; self#html_of_text fmt t
+ );
+ Format.fprintf fmt "@}@}"
+ )
+ l;
+
+ Format.fprintf fmt "@}@}@}@}"
+
+ (** Print html code for a module. *)
+ method html_of_module fmt ?(info=true) ?(complete=true) ?(with_link=true) m =
let (html_file, _) = Naming.html_files m.m_name in
let father = Name.father m.m_name in
- let buf = Buffer.create 32 in
- let p = Printf.bprintf in
- p buf "<pre>%s " (self#keyword "module");
- (
- if with_link then
- p buf "<a href=\"%s\">%s</a>" html_file (Name.simple m.m_name)
- else
- p buf "%s" (Name.simple m.m_name)
- );
- p buf ": %s</pre>" (self#html_of_module_type father m.m_type);
- if info then
- p buf "%s" ((if complete then self#html_of_info else self#html_of_info_first_sentence) m.m_info)
+ Format.fprintf fmt "@{<pre>";
+ self#keyword fmt "module";
+ Format.pp_print_string fmt " ";
+
+ if with_link then
+ Format.fprintf fmt "@{<href \"%s\">%s@}" html_file (Name.simple m.m_name)
else
- ();
- Buffer.contents buf
+ Format.fprintf fmt "%s" (Name.simple m.m_name);
+
+ Format.pp_print_string fmt ": ";
+ self#html_of_module_type fmt father m.m_type;
+ Format.fprintf fmt "@}";
+ if info then
+ (if complete then self#html_of_info
+ else self#html_of_info_first_sentence) fmt m.m_info
+
- (** Return html code for a module type. *)
- method html_of_modtype ?(info=true) ?(complete=true) ?(with_link=true) mt =
+ (** Print html code for a module type. *)
+ method html_of_modtype fmt ?(info=true) ?(complete=true) ?(with_link=true) mt =
let (html_file, _) = Naming.html_files mt.mt_name in
let father = Name.father mt.mt_name in
- let buf = Buffer.create 32 in
- let p = Printf.bprintf in
- p buf "<pre>%s " (self#keyword "module type");
- (
- if with_link then
- p buf "<a href=\"%s\">%s</a>" html_file (Name.simple mt.mt_name)
- else
- p buf "%s" (Name.simple mt.mt_name)
- );
+ Format.fprintf fmt "@{<pre>";
+ self#keyword fmt "module type";
+ Format.pp_print_string fmt " ";
+
+ if with_link then
+ Format.fprintf fmt "@{<href \"%s\">%s@}" html_file (Name.simple mt.mt_name)
+ else
+ Format.fprintf fmt "%s" (Name.simple mt.mt_name);
+
(match mt.mt_type with
None -> ()
- | Some mtyp -> p buf " = %s" (self#html_of_module_type father mtyp)
+ | Some mtyp ->
+ Format.pp_print_string fmt " = ";
+ self#html_of_module_type fmt father mtyp
);
- Buffer.add_string buf "</pre>";
+ Format.fprintf fmt "@}";
if info then
- p buf "%s" ((if complete then self#html_of_info else self#html_of_info_first_sentence) mt.mt_info)
- else
- ();
- Buffer.contents buf
+ (if complete then self#html_of_info else self#html_of_info_first_sentence) fmt mt.mt_info
- (** Return html code for an included module. *)
- method html_of_included_module im =
- "<pre>"^(self#keyword "include")^" "^
+ (** Print html code for an included module. *)
+ method html_of_included_module fmt im =
+ Format.fprintf fmt "@{<pre>";
+ self#keyword fmt "include";
+ Format.pp_print_string fmt " ";
(
match im.im_module with
- None ->
- im.im_name
+ None -> Format.pp_print_string fmt im.im_name
| Some mmt ->
let (file, name) =
match mmt with
@@ -1082,87 +1136,95 @@ class html =
let (html_file, _) = Naming.html_files mt.mt_name in
(html_file, mt.mt_name)
in
- "<a href=\""^file^"\">"^(Name.simple name)^"</a>"
- )^
- "</pre>\n"
+ Format.fprintf fmt "@{<href \"%s\">%s@}" file (Name.simple name)
+ );
+ Format.fprintf fmt "@}"
- (** Return html code for a class. *)
- method html_of_class ?(complete=true) ?(with_link=true) c =
+ (** Print html code for a class. *)
+ method html_of_class fmt ?(complete=true) ?(with_link=true) c =
let father = Name.father c.cl_name in
Odoc_info.reset_type_names ();
- let buf = Buffer.create 32 in
let (html_file, _) = Naming.html_files c.cl_name in
- let p = Printf.bprintf in
- p buf "<pre>%s " (self#keyword "class");
+ Format.fprintf fmt "@{<pre>";
+ self#keyword fmt "class";
+ Format.pp_print_string fmt " ";
(* we add a html tag, the same as for a type so we can
go directly here when the class name is used as a type name *)
- p buf "<a name=\"%s\"></a>"
+ Format.fprintf fmt "@{<mark \"%s\">@}"
(Naming.type_target
{ ty_name = c.cl_name ;
ty_info = None ; ty_parameters = [] ;
ty_kind = Type_abstract ; ty_manifest = None ;
ty_loc = Odoc_info.dummy_loc });
print_DEBUG "html#html_of_class : virtual or not" ;
- if c.cl_virtual then p buf "%s " (self#keyword "virtual") else ();
+ if c.cl_virtual then
+ (
+ self#keyword fmt "virtual";
+ Format.pp_print_string fmt " "
+ );
(
match c.cl_type_parameters with
[] -> ()
| l ->
- p buf "[%s] "
- (self#html_of_type_expr_list father ", " l)
+ Format.pp_print_string fmt "[";
+ self#html_of_type_expr_list fmt father ", " l;
+ Format.pp_print_string fmt "]"
);
print_DEBUG "html#html_of_class : with link or not" ;
(
if with_link then
- p buf "<a href=\"%s\">%s</a>" html_file (Name.simple c.cl_name)
+ Format.fprintf fmt "@{<href \"%s\">%s@}" html_file (Name.simple c.cl_name)
else
- p buf "%s" (Name.simple c.cl_name)
+ Format.pp_print_string fmt (Name.simple c.cl_name)
);
- Buffer.add_string buf " : " ;
- Buffer.add_string buf (self#html_of_class_type_expr father c.cl_type);
- Buffer.add_string buf "</pre>" ;
+ Format.pp_print_string fmt " : " ;
+ self#html_of_class_type_expr fmt father c.cl_type;
+ Format.fprintf fmt "@}";
print_DEBUG "html#html_of_class : info" ;
- Buffer.add_string buf
- ((if complete then self#html_of_info else self#html_of_info_first_sentence) c.cl_info);
- Buffer.contents buf
+ (if complete then self#html_of_info else self#html_of_info_first_sentence) fmt c.cl_info
- (** Return html code for a class type. *)
- method html_of_class_type ?(complete=true) ?(with_link=true) ct =
+ (** Print html code for a class type. *)
+ method html_of_class_type fmt ?(complete=true) ?(with_link=true) ct =
Odoc_info.reset_type_names ();
let father = Name.father ct.clt_name in
- let buf = Buffer.create 32 in
- let p = Printf.bprintf in
let (html_file, _) = Naming.html_files ct.clt_name in
- p buf "<pre>%s " (self#keyword "class type");
+ Format.fprintf fmt "@{<pre>";
+ self#keyword fmt "class type";
+ Format.pp_print_string fmt " ";
(* we add a html tag, the same as for a type so we can
go directly here when the class type name is used as a type name *)
- p buf "<a name=\"%s\"></a>"
+ Format.fprintf fmt "@{<mark \"%s\">@}"
(Naming.type_target
{ ty_name = ct.clt_name ;
ty_info = None ; ty_parameters = [] ;
ty_kind = Type_abstract ; ty_manifest = None ;
ty_loc = Odoc_info.dummy_loc });
- if ct.clt_virtual then p buf "%s "(self#keyword "virtual") else ();
+ if ct.clt_virtual then
+ (
+ self#keyword fmt "virtual";
+ Format.pp_print_string fmt " "
+ );
(
match ct.clt_type_parameters with
[] -> ()
- | l -> p buf "[%s] " (self#html_of_type_expr_list father ", " l)
+ | l ->
+ Format.pp_print_string fmt "[";
+ self#html_of_type_expr_list fmt father ", " l;
+ Format.pp_print_string fmt "]"
);
if with_link then
- p buf "<a href=\"%s\">%s</a>" html_file (Name.simple ct.clt_name)
+ Format.fprintf fmt "@{<href \"%s\">%s@}" html_file (Name.simple ct.clt_name)
else
- p buf "%s" (Name.simple ct.clt_name);
+ Format.pp_print_string fmt (Name.simple ct.clt_name);
- Buffer.add_string buf " = ";
- Buffer.add_string buf (self#html_of_class_type_expr father ct.clt_type);
- Buffer.add_string buf "</pre>";
- Buffer.add_string buf ((if complete then self#html_of_info else self#html_of_info_first_sentence) ct.clt_info);
+ Format.pp_print_string fmt " = ";
+ self#html_of_class_type_expr fmt father ct.clt_type;
+ Format.fprintf fmt "@}";
+ (if complete then self#html_of_info else self#html_of_info_first_sentence) fmt ct.clt_info
- Buffer.contents buf
-
- (** Return html code to represent a dag, represented as in Odoc_dag2html. *)
+ (** Get html code to represent a dag, represented as in Odoc_dag2html. *)
method html_of_dag dag =
let f n =
let (name, cct_opt) = n.Odoc_dag2html.valu in
@@ -1184,12 +1246,14 @@ class html =
let a = Array.map f dag.Odoc_dag2html.dag in
Odoc_dag2html.html_of_dag { Odoc_dag2html.dag = a }
- (** Return html code for a module comment.*)
- method html_of_module_comment text =
- "<br>\n"^(self#html_of_text text)^"<br><br>\n"
+ (** Print html code for a module comment.*)
+ method html_of_module_comment fmt text =
+ Format.pp_print_string fmt "<br>\n";
+ self#html_of_text fmt text;
+ Format.pp_print_string fmt "<br><br>\n"
- (** Return html code for a class comment.*)
- method html_of_class_comment text =
+ (** Print html code for a class comment.*)
+ method html_of_class_comment fmt text =
(* Add some style if there is no style for the first part of the text. *)
let text2 =
match text with
@@ -1197,10 +1261,10 @@ class html =
(Odoc_info.Title (2, None, [Odoc_info.Raw s])) :: q
| _ -> text
in
- self#html_of_text text2
+ self#html_of_text fmt text2
- (** Generate html code for the given list of inherited classes.*)
- method generate_inheritance_info chanout inher_l =
+ (** Print html code for the given list of inherited classes.*)
+ method generate_inheritance_info fmt inher_l =
let f inh =
match inh.ic_class with
None -> (* we can't make the link. *)
@@ -1226,8 +1290,7 @@ class html =
Odoc_info.List (List.map f inher_l)
]
in
- let html = self#html_of_text text in
- output_string chanout html
+ self#html_of_text fmt text
(** Generate html code for the inherited classes of the given class. *)
method generate_class_inheritance_info chanout cl =
@@ -1246,12 +1309,12 @@ class html =
iter_kind cl.cl_kind
(** Generate html code for the inherited classes of the given class type. *)
- method generate_class_type_inheritance_info chanout clt =
+ method generate_class_type_inheritance_info fmt clt =
match clt.clt_kind with
Class_signature ([], _) ->
()
| Class_signature (l, _) ->
- self#generate_inheritance_info chanout l
+ self#generate_inheritance_info fmt l
| Class_type _ ->
()
@@ -1264,13 +1327,10 @@ class html =
('a -> string) -> string -> string -> unit =
fun elements name info target title simple_file ->
try
- let chanout = open_out (Filename.concat !Odoc_args.target_dir simple_file) in
- output_string chanout
- (
- "<html>\n"^
- (self#header (self#inner_title title)) ^
- "<body>\n"^
- "<center><h1>"^title^"</h1></center>\n");
+ let (fmt,chanout) = self#formatter_of_file (Filename.concat !Odoc_args.target_dir simple_file) in
+ Format.fprintf fmt "@{<html>";
+ self#header fmt (self#inner_title title);
+ Format.fprintf fmt "@{<body>@{<center>@{<h1>%s@}@}" title;
let sorted_elements = List.sort
(fun e1 -> fun e2 -> compare (Name.simple (name e1)) (Name.simple (name e2)))
@@ -1280,16 +1340,12 @@ class html =
let f_ele e =
let simple_name = Name.simple (name e) in
let father_name = Name.father (name e) in
- output_string chanout
- ("<tr><td><a href=\""^(target e)^"\">"^simple_name^"</a> "^
- (if simple_name <> father_name then
- "["^"<a href=\""^(fst (Naming.html_files father_name))^"\">"^father_name^"</a>]"
- else
- ""
- )^
- "</td>\n"^
- "<td>"^(self#html_of_info_first_sentence (info e))^"</td></tr>\n"
- )
+ Format.fprintf fmt "@{<tr>@{<td>@{<href \"%s\">%s@} " (target e) simple_name;
+ if simple_name <> father_name then
+ Format.fprintf fmt "[@{<href \"%s\">%s@}]" (fst (Naming.html_files father_name)) father_name;
+ Format.fprintf fmt "@}@{<td>";
+ self#html_of_info_first_sentence fmt (info e);
+ Format.fprintf fmt "@}@}"
in
let f_group l =
match l with
@@ -1300,13 +1356,13 @@ class html =
'A'..'Z' as c -> String.make 1 c
| _ -> ""
in
- output_string chanout ("<tr><td align=\"left\"><br>"^s^"</td></tr>\n");
+ Format.fprintf fmt "@{<tr>@{<td align=\"left\"><br>%s@}@}" s;
List.iter f_ele l
in
- output_string chanout "<table>\n";
+ Format.fprintf fmt "@{<table>";
List.iter f_group groups ;
- output_string chanout "</table><br>\n" ;
- output_string chanout "</body>\n</html>";
+ Format.fprintf fmt "@}<br>\n@}@}";
+ Format.pp_print_flush fmt ();
close_out chanout
with
Sys_error s ->
@@ -1331,44 +1387,40 @@ class html =
let (html_file, _) = Naming.html_files cl.cl_name in
let type_file = Naming.file_type_class_complete_target cl.cl_name in
try
- let chanout = open_out (Filename.concat !Odoc_args.target_dir html_file) in
+ let (fmt, chanout) = self#formatter_of_file (Filename.concat !Odoc_args.target_dir html_file) in
let pre_name = opt (fun c -> c.cl_name) pre in
let post_name = opt (fun c -> c.cl_name) post in
- output_string chanout
- ("<html>\n"^
- (self#header
- ~nav: (Some (pre_name, post_name, cl.cl_name))
- (self#inner_title cl.cl_name)
- )^
- "<body>\n"^
- (self#navbar pre_name post_name cl.cl_name)^
- "<center><h1>"^Odoc_messages.clas^" "^
- (if cl.cl_virtual then "virtual " else "")^
- "<a href=\""^type_file^"\">"^cl.cl_name^"</a>"^
- "</h1></center>\n"^
- "<br>\n"^
- (self#html_of_class ~with_link: false cl)
- );
+ Format.fprintf fmt "@{<html>";
+ self#header fmt
+ ~nav: (Some (pre_name, post_name, cl.cl_name))
+ (self#inner_title cl.cl_name);
+
+ Format.fprintf fmt "@{<body>";
+ self#navbar fmt pre_name post_name cl.cl_name;
+ Format.fprintf fmt "@{<center>@{<h1>%s %s@{<href \"%s\">%s@}@}@}<br>\n"
+ Odoc_messages.clas
+ (if cl.cl_virtual then "virtual " else "")
+ type_file
+ cl.cl_name;
+ self#html_of_class fmt ~with_link: false cl;
+
(* parameters *)
- output_string chanout
- (self#html_of_described_parameter_list (Name.father cl.cl_name) cl.cl_parameters);
+ self#html_of_described_parameter_list fmt (Name.father cl.cl_name) cl.cl_parameters;
(* class inheritance *)
- self#generate_class_inheritance_info chanout cl;
+ self#generate_class_inheritance_info fmt cl;
(* a horizontal line *)
- output_string chanout "<hr width=\"100%\">\n";
+ Format.pp_print_string fmt "<hr width=\"100%\">\n";
(* the various elements *)
List.iter
(fun element ->
match element with
- Class_attribute a ->
- output_string chanout (self#html_of_attribute a)
- | Class_method m ->
- output_string chanout (self#html_of_method m)
- | Class_comment t ->
- output_string chanout (self#html_of_class_comment t)
+ Class_attribute a -> self#html_of_attribute fmt a
+ | Class_method m -> self#html_of_method fmt m
+ | Class_comment t -> self#html_of_class_comment fmt t
)
(Class.class_elements ~trans:false cl);
- output_string chanout "</html>";
+ Format.fprintf fmt "@}@}";
+ Format.pp_print_flush fmt ();
close_out chanout;
(* generate the file with the complete class type *)
@@ -1386,41 +1438,37 @@ class html =
let (html_file, _) = Naming.html_files clt.clt_name in
let type_file = Naming.file_type_class_complete_target clt.clt_name in
try
- let chanout = open_out (Filename.concat !Odoc_args.target_dir html_file) in
+ let (fmt, chanout) = self#formatter_of_file (Filename.concat !Odoc_args.target_dir html_file) in
let pre_name = opt (fun ct -> ct.clt_name) pre in
let post_name = opt (fun ct -> ct.clt_name) post in
- output_string chanout
- ("<html>\n"^
- (self#header
- ~nav: (Some (pre_name, post_name, clt.clt_name))
- (self#inner_title clt.clt_name)
- )^
- "<body>\n"^
- (self#navbar pre_name post_name clt.clt_name)^
- "<center><h1>"^Odoc_messages.class_type^" "^
- (if clt.clt_virtual then "virtual " else "")^
- "<a href=\""^type_file^"\">"^clt.clt_name^"</a>"^
- "</h1></center>\n"^
- "<br>\n"^
- (self#html_of_class_type ~with_link: false clt)
- );
+ Format.fprintf fmt "@{<html>";
+ self#header fmt
+ ~nav: (Some (pre_name, post_name, clt.clt_name))
+ (self#inner_title clt.clt_name);
+ Format.fprintf fmt "@{<body>";
+ self#navbar fmt pre_name post_name clt.clt_name;
+ Format.fprintf fmt "@{<center>@{<h1>%s %s@{<href \"%s\">%s@}@}@}<br>\n"
+ Odoc_messages.class_type
+ (if clt.clt_virtual then "virtual " else "")
+ type_file
+ clt.clt_name;
+ self#html_of_class_type fmt ~with_link: false clt;
+
(* class inheritance *)
- self#generate_class_type_inheritance_info chanout clt;
+ self#generate_class_type_inheritance_info fmt clt;
(* a horizontal line *)
- output_string chanout "<hr width=\"100%\">\n";
+ Format.pp_print_string fmt "<hr width=\"100%\">\n";
(* the various elements *)
List.iter
(fun element ->
match element with
- Class_attribute a ->
- output_string chanout (self#html_of_attribute a)
- | Class_method m ->
- output_string chanout (self#html_of_method m)
- | Class_comment t ->
- output_string chanout (self#html_of_class_comment t)
+ Class_attribute a -> self#html_of_attribute fmt a
+ | Class_method m -> self#html_of_method fmt m
+ | Class_comment t -> self#html_of_class_comment fmt t
)
(Class.class_type_elements ~trans: false clt);
- output_string chanout "</html>";
+ Format.fprintf fmt "@}@}";
+ Format.pp_print_flush fmt ();
close_out chanout;
(* generate the file with the complete class type *)
@@ -1438,57 +1486,45 @@ class html =
try
let (html_file, _) = Naming.html_files mt.mt_name in
let type_file = Naming.file_type_module_complete_target mt.mt_name in
- let chanout = open_out (Filename.concat !Odoc_args.target_dir html_file) in
+ let (fmt, chanout) = self#formatter_of_file (Filename.concat !Odoc_args.target_dir html_file) in
let pre_name = opt (fun mt -> mt.mt_name) pre in
let post_name = opt (fun mt -> mt.mt_name) post in
- output_string chanout
- ("<html>\n"^
- (self#header
- ~nav: (Some (pre_name, post_name, mt.mt_name))
- (self#inner_title mt.mt_name)
- )^
- "<body>\n"^
- (self#navbar pre_name post_name mt.mt_name)^
- "<center><h1>"^Odoc_messages.module_type^
- " "^
- (match mt.mt_type with
- Some _ -> "<a href=\""^type_file^"\">"^mt.mt_name^"</a>"
- | None-> mt.mt_name
- )^
- "</h1></center>\n"^
- "<br>\n"^
- (self#html_of_modtype ~with_link: false mt)
- );
+ Format.fprintf fmt "@{<html>";
+ self#header fmt
+ ~nav: (Some (pre_name, post_name, mt.mt_name))
+ (self#inner_title mt.mt_name);
+ Format.fprintf fmt "@{<body>";
+ self#navbar fmt pre_name post_name mt.mt_name;
+ Format.fprintf fmt "@{<center>@{<h1>%s " Odoc_messages.module_type;
+ (match mt.mt_type with
+ Some _ -> Format.fprintf fmt "@{<href \"%s\">%s@}" type_file mt.mt_name
+ | None-> Format.pp_print_string fmt mt.mt_name
+ );
+ Format.fprintf fmt "@}@}<br>\n";
+ self#html_of_modtype fmt ~with_link: false mt;
+
(* parameters for functors *)
- output_string chanout (self#html_of_module_parameter_list "" (Module.module_type_parameters mt));
+ self#html_of_module_parameter_list fmt "" (Module.module_type_parameters mt);
(* a horizontal line *)
- output_string chanout "<hr width=\"100%\">\n";
+ Format.pp_print_string fmt "<hr width=\"100%\">\n";
(* module elements *)
List.iter
(fun ele ->
match ele with
- Element_module m ->
- output_string chanout (self#html_of_module ~complete: false m)
- | Element_module_type mt ->
- output_string chanout (self#html_of_modtype ~complete: false mt)
- | Element_included_module im ->
- output_string chanout (self#html_of_included_module im)
- | Element_class c ->
- output_string chanout (self#html_of_class ~complete: false c)
- | Element_class_type ct ->
- output_string chanout (self#html_of_class_type ~complete: false ct)
- | Element_value v ->
- output_string chanout (self#html_of_value v)
- | Element_exception e ->
- output_string chanout (self#html_of_exception e)
- | Element_type t ->
- output_string chanout (self#html_of_type t)
- | Element_module_comment text ->
- output_string chanout (self#html_of_module_comment text)
+ Element_module m -> self#html_of_module fmt ~complete: false m
+ | Element_module_type mt -> self#html_of_modtype fmt ~complete: false mt
+ | Element_included_module im -> self#html_of_included_module fmt im
+ | Element_class c ->self#html_of_class fmt ~complete: false c
+ | Element_class_type ct -> self#html_of_class_type fmt ~complete: false ct
+ | Element_value v -> self#html_of_value fmt v
+ | Element_exception e -> self#html_of_exception fmt e
+ | Element_type t -> self#html_of_type fmt t
+ | Element_module_comment text -> self#html_of_module_comment fmt text
)
(Module.module_type_elements mt);
- output_string chanout "</html>";
+ Format.fprintf fmt "@}@}";
+ Format.pp_print_flush fmt ();
close_out chanout;
(* generate html files for submodules *)
@@ -1520,55 +1556,48 @@ class html =
Odoc_info.verbose ("Generate for module "^modu.m_name);
let (html_file, _) = Naming.html_files modu.m_name in
let type_file = Naming.file_type_module_complete_target modu.m_name in
- let chanout = open_out (Filename.concat !Odoc_args.target_dir html_file) in
+ let (fmt, chanout) = self#formatter_of_file
+ (Filename.concat !Odoc_args.target_dir html_file)
+ in
+
let pre_name = opt (fun m -> m.m_name) pre in
let post_name = opt (fun m -> m.m_name) post in
- output_string chanout
- ("<html>\n"^
- (self#header
- ~nav: (Some (pre_name, post_name, modu.m_name))
- (self#inner_title modu.m_name)
- ) ^
- "<body>\n"^
- (self#navbar pre_name post_name modu.m_name)^
- "<center><h1>"^(if Module.module_is_functor modu then Odoc_messages.functo else Odoc_messages.modul)^
- " "^
- "<a href=\""^type_file^"\">"^modu.m_name^"</a>"^
- "</h1></center>\n"^
- "<br>\n"^
- (self#html_of_module ~with_link: false modu)
- );
+ Format.fprintf fmt "@{<html>";
+ self#header fmt
+ ~nav: (Some (pre_name, post_name, modu.m_name))
+ (self#inner_title modu.m_name);
+
+ Format.fprintf fmt "@{<body>";
+ self#navbar fmt pre_name post_name modu.m_name ;
+ Format.fprintf fmt "@{<center>@{<h1>%s @{<href \"%s\">%s@}@}@}<br>\n"
+ (if Module.module_is_functor modu then Odoc_messages.functo else Odoc_messages.modul)
+ type_file modu.m_name;
+
+ self#html_of_module fmt ~with_link: false modu;
+
(* parameters for functors *)
- output_string chanout (self#html_of_module_parameter_list "" (Module.module_parameters modu));
+ self#html_of_module_parameter_list fmt "" (Module.module_parameters modu);
(* a horizontal line *)
- output_string chanout "<hr width=\"100%\">\n";
+ Format.fprintf fmt "<hr width=\"100%%\">\n";
(* module elements *)
List.iter
(fun ele ->
print_DEBUG "html#generate_for_module : ele ->";
match ele with
- Element_module m ->
- output_string chanout (self#html_of_module ~complete: false m)
- | Element_module_type mt ->
- output_string chanout (self#html_of_modtype ~complete: false mt)
- | Element_included_module im ->
- output_string chanout (self#html_of_included_module im)
- | Element_class c ->
- output_string chanout (self#html_of_class ~complete: false c)
- | Element_class_type ct ->
- output_string chanout (self#html_of_class_type ~complete: false ct)
- | Element_value v ->
- output_string chanout (self#html_of_value v)
- | Element_exception e ->
- output_string chanout (self#html_of_exception e)
- | Element_type t ->
- output_string chanout (self#html_of_type t)
- | Element_module_comment text ->
- output_string chanout (self#html_of_module_comment text)
+ Element_module m -> self#html_of_module fmt ~complete: false m
+ | Element_module_type mt -> self#html_of_modtype fmt ~complete: false mt
+ | Element_included_module im -> self#html_of_included_module fmt im
+ | Element_class c -> self#html_of_class fmt ~complete: false c
+ | Element_class_type ct -> self#html_of_class_type fmt ~complete: false ct
+ | Element_value v ->self#html_of_value fmt v
+ | Element_exception e ->self#html_of_exception fmt e
+ | Element_type t -> self#html_of_type fmt t
+ | Element_module_comment text -> self#html_of_module_comment fmt text
)
(Module.module_elements modu);
- output_string chanout "</html>";
+ Format.fprintf fmt "@}@}";
+ Format.pp_print_flush fmt ();
close_out chanout;
(* generate html files for submodules *)
@@ -1594,42 +1623,35 @@ class html =
method generate_index module_list =
try
let title = match !Odoc_args.title with None -> "" | Some t -> self#escape t in
+ let (fmt, chanout) = self#formatter_of_file (Filename.concat !Odoc_args.target_dir index) in
let index_if_not_empty l url m =
match l with
- [] -> ""
- | _ -> "<a href=\""^url^"\">"^m^"</a><br>\n"
+ [] -> ()
+ | _ -> Format.fprintf fmt "@{<href \"%s\">%s@}<br>\n" url m
in
- let chanout = open_out (Filename.concat !Odoc_args.target_dir index) in
- output_string chanout
- (
- "<html>\n"^
- (self#header self#title) ^
- "<body>\n"^
- "<center><h1>"^title^"</h1></center>\n"^
- (index_if_not_empty list_types index_types Odoc_messages.index_of_types)^
- (index_if_not_empty list_exceptions index_exceptions Odoc_messages.index_of_exceptions)^
- (index_if_not_empty list_values index_values Odoc_messages.index_of_values)^
- (index_if_not_empty list_attributes index_attributes Odoc_messages.index_of_attributes)^
- (index_if_not_empty list_methods index_methods Odoc_messages.index_of_methods)^
- (index_if_not_empty list_classes index_classes Odoc_messages.index_of_classes)^
- (index_if_not_empty list_class_types index_class_types Odoc_messages.index_of_class_types)^
- (index_if_not_empty list_modules index_modules Odoc_messages.index_of_modules)^
- (index_if_not_empty list_module_types index_module_types Odoc_messages.index_of_module_types)^
- "<br>\n"^
- "<table border=\"0\">\n"^
- (String.concat ""
- (List.map
- (fun m ->
- let (html, _) = Naming.html_files m.m_name in
- "<tr><td><a href=\""^html^"\">"^m.m_name^"</a></td>"^
- "<td>"^(self#html_of_info_first_sentence m.m_info)^"</td></tr>\n")
- module_list
- )
- )^
- "</table>\n"^
- "</body>\n"^
- "</html>"
- );
+ Format.fprintf fmt "@{<html>";
+ self#header fmt self#title;
+ Format.fprintf fmt "@{<body>@{<center>@{<h1>%s@}@}" title;
+ index_if_not_empty list_types index_types Odoc_messages.index_of_types ;
+ index_if_not_empty list_exceptions index_exceptions Odoc_messages.index_of_exceptions ;
+ index_if_not_empty list_values index_values Odoc_messages.index_of_values ;
+ index_if_not_empty list_attributes index_attributes Odoc_messages.index_of_attributes ;
+ index_if_not_empty list_methods index_methods Odoc_messages.index_of_methods ;
+ index_if_not_empty list_classes index_classes Odoc_messages.index_of_classes ;
+ index_if_not_empty list_class_types index_class_types Odoc_messages.index_of_class_types ;
+ index_if_not_empty list_modules index_modules Odoc_messages.index_of_modules ;
+ index_if_not_empty list_module_types index_module_types Odoc_messages.index_of_module_types ;
+ Format.fprintf fmt "<br>\n@{<table border=\"0\">";
+ List.iter
+ (fun m ->
+ let (html, _) = Naming.html_files m.m_name in
+ Format.fprintf fmt "@{<tr>@{<td>@{<href \"%s\">%s@}@}@{<td>" html m.m_name;
+ self#html_of_info_first_sentence fmt m.m_info;
+ Format.fprintf fmt "@}@}"
+ )
+ module_list;
+ Format.fprintf fmt "@}@}@}";
+ Format.pp_print_flush fmt ();
close_out chanout
with
Sys_error s ->
@@ -1780,9 +1802,48 @@ class html =
prerr_endline s ;
incr Odoc_info.errors
+ method init_formatter fmt =
+ let htag s =
+ try
+ let i = String.index s ' ' in
+ String.sub s 0 i, String.sub s (i + 1) (String.length s - i - 1)
+ with Not_found -> s, ""
+ in
+
+ let mark_open_tag s =
+ let tag, vals = htag s in
+ match tag with
+ | "href" -> "<a href=" ^ vals ^ ">"
+ | "mark" -> "<a name=" ^ vals ^ ">"
+ | "ul" | "li" | "ol" | "html" | "body"
+ | "table" | "tr" | "td" | "head" ->
+ "<" ^ tag ^(if vals = "" then "" else " "^vals)^ ">\n"
+ | t -> "<" ^ t ^ " " ^ vals ^ ">"
+ in
+ let mark_close_tag s =
+ let tag, vals = htag s in
+ match tag with
+ | "href" -> "</a>"
+ | "mark" -> "</a>"
+ | "ul" | "li" | "ol" | "html" | "body" | "pre"
+ | "table" | "tr" | "td" | "head" -> "</" ^ tag ^ ">\n"
+ | t -> "</" ^ t ^ ">"
+ in
+ Format.pp_set_formatter_tag_functions fmt
+ {(Format.pp_get_formatter_tag_functions fmt ()) with
+ Format.mark_close_tag = mark_close_tag;
+ Format.mark_open_tag = mark_open_tag}
+
+ method formatter_of_file file =
+ let chanout = open_out file in
+ let fmt = Format.formatter_of_out_channel chanout in
+ self#init_formatter fmt;
+ (fmt, chanout)
+
initializer
Odoc_ocamlhtml.html_of_comment :=
- (fun s -> self#html_of_text (Odoc_text.Texter.text_of_string s))
+ (fun fmt -> fun s -> self#html_of_text fmt (Odoc_text.Texter.text_of_string s));
+
end
diff --git a/ocamldoc/odoc_ocamlhtml.mll b/ocamldoc/odoc_ocamlhtml.mll
index 5881f4a59..5e847a112 100644
--- a/ocamldoc/odoc_ocamlhtml.mll
+++ b/ocamldoc/odoc_ocamlhtml.mll
@@ -80,7 +80,8 @@ let create_hashtable size init =
(** The function used to return html code for the given comment body. *)
let html_of_comment = ref
- (fun (s : string) -> "<b>Odoc_ocamlhtml.html_of_comment not initialized</b>")
+ (fun (fmt: Format.formatter) (s : string) ->
+ Format.fprintf fmt "@{<b>Odoc_ocamlhtml.html_of_comment not initialized@}")
let keyword_table =
create_hashtable 149 [
@@ -169,28 +170,28 @@ let make_margin () =
let print_comment () =
let s = Buffer.contents comment_buffer in
let len = String.length s in
- let code =
- if len < 1 then
- "<span class=\""^comment_class^"\">(*"^(escape s)^"*)</span>"
- else
- match s.[0] with
- '*' ->
- (
- try
- let html = !html_of_comment (String.sub s 1 (len-1)) in
- "</code><table><tr><td>"^(make_margin ())^"</td><td>"^
- "<span class=\""^comment_class^"\">"^
- "(**"^html^"*)"^
- "</span></td></tr></table><code class=\""^code_class^"\">"
- with
- e ->
- prerr_endline (Printexc.to_string e);
- "<span class=\""^comment_class^"\">(*"^(escape s)^"*)</span>"
- )
- | _ ->
- "<span class=\""^comment_class^"\">(*"^(escape s)^"*)</span>"
- in
- print ~esc: false code
+ if len < 1 then
+ Format.fprintf !fmt "@{<span class=\"%s\">(*%s*)@}" comment_class (escape s)
+ else
+ match s.[0] with
+ '*' ->
+ (
+ try
+ Format.pp_print_string !fmt
+ ("</code><table><tr><td>"^(make_margin ())^"</td><td>"^
+ "<span class=\""^comment_class^"\">"^
+ "(**");
+ !html_of_comment !fmt (String.sub s 1 (len-1));
+ Format.pp_print_string !fmt
+ ("*)</span></td></tr></table><code class=\""^code_class^"\">")
+ with
+ e ->
+ prerr_endline (Printexc.to_string e);
+ Format.pp_print_string !fmt
+ ("<span class=\""^comment_class^"\">(*"^(escape s)^"*)</span>")
+ )
+ | _ ->
+ Format.fprintf !fmt "@{<span class=\"%s\">(*%s*)@}" comment_class (escape s)
(** To buffer string literals *)
@@ -494,45 +495,36 @@ and string = parse
string lexbuf }
{
-let html_of_code ?(with_pre=true) code =
+let html_of_code formatter ?(with_pre=true) code =
let old_pre = !pre in
let old_margin = !margin in
let old_comment_buffer = Buffer.contents comment_buffer in
let old_string_buffer = Buffer.contents string_buffer in
- let buf = Buffer.create 256 in
let old_fmt = !fmt in
- fmt := Format.formatter_of_buffer buf ;
+ let buf = Buffer.create 256 in
+ fmt := Format.formatter_of_buffer buf;
pre := with_pre;
margin := 0;
+ Format.fprintf formatter "@{<code class=\"%s\">" code_class ;
+ (
+ try
+ let lexbuf = Lexing.from_string code in
+ ignore (token lexbuf);
+ Format.pp_print_flush !fmt ();
+ Format.pp_print_string formatter (Buffer.contents buf)
+ with
+ _ ->
+ Format.pp_print_string formatter (escape code)
+ );
+ Format.fprintf formatter "@}";
- let start = "<code class=\""^code_class^"\">" in
- let ending = "</code>" in
- let html =
- (
- try
- print ~esc: false start ;
- let lexbuf = Lexing.from_string code in
- let _ = token lexbuf in
- print ~esc: false ending ;
- Format.pp_print_flush !fmt () ;
- Buffer.contents buf
- with
- _ ->
- (* flush str_formatter because we already output
- something in it *)
- Format.pp_print_flush !fmt () ;
- start^code^ending
- )
- in
pre := old_pre;
+ fmt := old_fmt;
margin := old_margin ;
Buffer.reset comment_buffer;
Buffer.add_string comment_buffer old_comment_buffer ;
Buffer.reset string_buffer;
Buffer.add_string string_buffer old_string_buffer ;
- fmt := old_fmt ;
-
- html
}