Permalink
Browse files

Initial revision

git-svn-id: http://svn.wikimedia.org/svnroot/mediawiki/trunk/phase3/math@1284 dd0e9695-b195-4be7-bd10-2dea1a65a6b6
  • Loading branch information...
0 parents commit ca3a6606877f60c9e77c00e7fa8ec7b7eb7c4238 lcrocker committed Apr 14, 2003
Showing with 1,096 additions and 0 deletions.
  1. +64 −0 Makefile
  2. +18 −0 README
  3. +3 −0 TODO
  4. +119 −0 html.ml
  5. +5 −0 html.mli
  6. +90 −0 lexer.mll
  7. +20 −0 mathml.ml
  8. +1 −0 mathml.mli
  9. +103 −0 parser.mly
  10. +29 −0 render.ml
  11. +20 −0 render_info.mli
  12. +19 −0 tex.mli
  13. +453 −0 texutil.ml
  14. +11 −0 texutil.mli
  15. +34 −0 texvc.ml
  16. +62 −0 texvc_cgi.ml
  17. +25 −0 texvc_test.ml
  18. +3 −0 texvc_tex.ml
  19. +17 −0 util.ml
@@ -0,0 +1,64 @@
+OBJ=render_info.cmo tex.cmo texutil.cmo parser.cmo lexer.cmo texvc.cmo \
+render_info.cmx tex.cmx texutil.cmx parser.cmx lexer.cmx texvc.cmx \
+lexer.cmi parser.cmi render_info.cmi tex.cmi texutil.cmi texvc.cmi \
+lexer.o parser.o render_info.o tex.o texutil.o texvc.o \
+lexer.ml parser.ml parser.mli texvc texvc.bc texvc_test.cmo \
+texvc_test.cmx texvc_test.cmi texvc_test.o texvc_test util.o \
+util.cmo util.cmx util.cmi texvc_cgi.cmi texvc_cgi texvc_cgi.cmo \
+render.o render.cmi render.cmo render.cmx texvc_tex.cmx \
+texvc_tex.o texvc_tex.cmi texvc_tex html.cmi html.cmo html.cmx \
+html.o mathml.cmi mathml.cmo mathml.cmx mathml.o
+CGIPATH=-I /usr/lib/ocaml/cgi -I /usr/lib/ocaml/netstring -I /usr/lib/ocaml/pcre
+
+all: texvc texvc_test texvc_tex
+texvc.bc: util.cmo parser.cmo html.cmo mathml.cmo texutil.cmo render.cmo lexer.cmo texvc.cmo
+ ocamlc -o $@ unix.cma $^
+texvc: util.cmx parser.cmx html.cmx mathml.cmx texutil.cmx render.cmx lexer.cmx texvc.cmx
+ ocamlopt -o $@ unix.cmxa $^
+texvc_test: util.cmx parser.cmx html.cmx mathml.cmx texutil.cmx lexer.cmx texvc_test.cmx
+ ocamlopt -o $@ $^
+texvc_tex: util.cmx parser.cmx html.cmx mathml.cmx texutil.cmx lexer.cmx texvc_tex.cmx
+ ocamlopt -o $@ $^
+%.ml: %.mll
+ ocamllex $<
+%.mli %.ml: %.mly
+ ocamlyacc $<
+%.cmo: %.ml
+ ocamlc -c $<
+%.cmx: %.ml
+ ocamlopt -c $<
+%.cmi: %.mli
+ ocamlc -c $<
+texvc_cgi.cmo: texvc_cgi.ml
+ ocamlc -c $(CGIPATH) $<
+texvc_cgi: util.cmo parser.cmo texutil.cmo render.cmo lexer.cmo texvc_cgi.cmo
+ ocamlc -o $@ unix.cma $(CGIPATH) pcre.cma netstring.cma cgi.cma $^
+ chmod g-w $@
+clean:
+ rm -f $(OBJ)
+
+html.cmo: render_info.cmi tex.cmi util.cmo html.cmi
+html.cmx: render_info.cmi tex.cmi util.cmx html.cmi
+html.cmi: tex.cmi
+lexer.cmo: parser.cmi render_info.cmi tex.cmi texutil.cmi
+lexer.cmx: parser.cmx render_info.cmi tex.cmi texutil.cmx
+mathml.cmo: tex.cmi mathml.cmi
+mathml.cmx: tex.cmi mathml.cmi
+mathml.cmi: tex.cmi
+parser.cmo: render_info.cmi tex.cmi parser.cmi
+parser.cmx: render_info.cmi tex.cmi parser.cmi
+parser.cmi: render_info.cmi tex.cmi
+render.cmo: texutil.cmi util.cmo
+render.cmx: texutil.cmx util.cmx
+tex.cmi: render_info.cmi
+texutil.cmo: html.cmi parser.cmi render_info.cmi tex.cmi util.cmo texutil.cmi
+texutil.cmx: html.cmx parser.cmx render_info.cmi tex.cmi util.cmx texutil.cmi
+texutil.cmi: parser.cmi tex.cmi
+texvc.cmo: html.cmi lexer.cmo mathml.cmi parser.cmi render.cmo texutil.cmi util.cmo
+texvc.cmx: html.cmx lexer.cmx mathml.cmx parser.cmx render.cmx texutil.cmx util.cmx
+texvc_cgi.cmo: lexer.cmo parser.cmi render.cmo texutil.cmi util.cmo
+texvc_cgi.cmx: lexer.cmx parser.cmx render.cmx texutil.cmx util.cmx
+texvc_test.cmo: html.cmi lexer.cmo parser.cmi texutil.cmi util.cmo
+texvc_test.cmx: html.cmx lexer.cmx parser.cmx texutil.cmx util.cmx
+texvc_tex.cmo: lexer.cmo parser.cmi texutil.cmi util.cmo
+texvc_tex.cmx: lexer.cmx parser.cmx texutil.cmx util.cmx
@@ -0,0 +1,18 @@
+texvc output format is like that:
+ +%5 ok, but not html or mathml
+ c%5%h ok, conservative html, no mathml
+ m%5%h ok, moderate html, no mathml
+ l%5%h ok, liberal html, no mathml
+ C%5%h\0%m ok, conservative html, with mathml
+ M%5%h\0%m ok, moderate html, with mathml
+ L%5%h\0%m ok, liberal html, with mathml
+ X%5%m ok, no html, with mathml
+ S syntax error
+ E lexing error
+ F%s unknown function %s
+ - other error
+
+\0 - null character
+%5 - md5, 32 hex characters
+%h - html code, without \0 characters
+%m - mathml code, without \0 characters
@@ -0,0 +1,3 @@
+* It would be better if PNGs were transparent
+* CJK support
+* Documentation, in particular about instalation of Latex support for Unicode
@@ -0,0 +1,119 @@
+open Render_info
+open Tex
+open Util
+
+exception Too_difficult_for_html
+type context = CTX_NORMAL | CTX_IT | CTX_RM
+type conservativeness_t = CONSERVATIVE | MODERATE | LIBERAL
+
+let conservativeness = ref CONSERVATIVE
+let html_liberal () = conservativeness := LIBERAL
+let html_moderate () = if !conservativeness = CONSERVATIVE then conservativeness := MODERATE else ()
+
+
+let new_ctx = function
+ FONTFORCE_IT -> CTX_IT
+ | FONTFORCE_RM -> CTX_RM
+let font_render lit = function
+ (_, FONT_UFH) -> lit
+ | (_, FONT_UF) -> lit
+ | (CTX_IT,FONT_RTI) -> raise Too_difficult_for_html
+ | (_, FONT_RTI) -> lit
+ | (CTX_IT,FONT_RM) -> "<i>"^lit^"</i>"
+ | (_, FONT_RM) -> lit
+ | (CTX_RM,FONT_IT) -> lit
+ | (_, FONT_IT) -> "<i>"^lit^"</i>"
+
+let rec html_render_flat ctx = function
+ TEX_LITERAL (HTMLABLE (ft,_,sh))::r -> (html_liberal (); (font_render sh (ctx,ft))^html_render_flat ctx r)
+ | TEX_LITERAL (HTMLABLEC(ft,_,sh))::r -> (font_render sh (ctx,ft))^html_render_flat ctx r
+ | TEX_LITERAL (MHTMLABLEC(ft,_,sh,_,_))::r -> (font_render sh (ctx,ft))^html_render_flat ctx r
+ | TEX_LITERAL (HTMLABLEM(ft,_,sh))::r -> (html_moderate(); (font_render sh (ctx,ft))^html_render_flat ctx r)
+ | TEX_LITERAL (HTMLABLE_BIG (_,sh))::r -> (html_liberal (); sh^html_render_flat ctx r)
+ | TEX_FUN1hl (_,(f1,f2),a)::r -> f1^(html_render_flat ctx [a])^f2^html_render_flat ctx r
+ | TEX_FUN1hf (_,ff,a)::r -> (html_render_flat (new_ctx ff) [a])^html_render_flat ctx r
+ | TEX_DECLh (_,ff,a)::r -> (html_render_flat (new_ctx ff) a)^html_render_flat ctx r
+ | TEX_CURLY ls::r -> html_render_flat ctx (ls @ r)
+ | TEX_DQ (a,b)::r -> (html_liberal ();
+ let bs = html_render_flat ctx [b] in match html_render_size ctx a with
+ true, s -> raise Too_difficult_for_html
+ | false, s -> s^"<sub>"^bs^"</sub>")^html_render_flat ctx r
+ | TEX_UQ (a,b)::r -> (html_liberal ();
+ let bs = html_render_flat ctx [b] in match html_render_size ctx a with
+ true, s -> raise Too_difficult_for_html
+ | false, s -> s^"<sup>"^bs^"</sup>")^html_render_flat ctx r
+ | TEX_FQ (a,b,c)::r -> (html_liberal ();
+ (let bs = html_render_flat ctx [b] in let cs = html_render_flat ctx [c] in
+ match html_render_size ctx a with
+ true, s -> raise Too_difficult_for_html
+ | false, s -> s^"<sub>"^bs^"</sub><sup>"^cs^"</sup>")^html_render_flat ctx r)
+ | TEX_BOX (_,s)::r -> s^html_render_flat ctx r
+ | TEX_LITERAL (TEX_ONLY _)::_ -> raise Too_difficult_for_html
+ | TEX_FUN1 _::_ -> raise Too_difficult_for_html
+ | TEX_FUN2 _::_ -> raise Too_difficult_for_html
+ | TEX_FUN2h _::_ -> raise Too_difficult_for_html
+ | TEX_FUN2sq _::_ -> raise Too_difficult_for_html
+ | TEX_INFIX _::_ -> raise Too_difficult_for_html
+ | TEX_INFIXh _::_ -> raise Too_difficult_for_html
+ | TEX_MATRIX _::_ -> raise Too_difficult_for_html
+ | TEX_LR _::_ -> raise Too_difficult_for_html
+ | TEX_BIG _::_ -> raise Too_difficult_for_html
+ | [] -> ""
+and html_render_size ctx = function
+ TEX_LITERAL (HTMLABLE_BIG (_,sh)) -> true,sh
+ | x -> false,html_render_flat ctx [x]
+
+let rec html_render_deep ctx = function
+ TEX_LITERAL (HTMLABLE (ft,_,sh))::r -> (html_liberal (); ("",(font_render sh (ctx,ft)),"")::html_render_deep ctx r)
+ | TEX_LITERAL (HTMLABLEM(ft,_,sh))::r -> (html_moderate(); ("",(font_render sh (ctx,ft)),"")::html_render_deep ctx r)
+ | TEX_LITERAL (HTMLABLEC(ft,_,sh))::r -> ("",(font_render sh (ctx,ft)),"")::html_render_deep ctx r
+ | TEX_LITERAL (MHTMLABLEC(ft,_,sh,_,_))::r -> ("",(font_render sh (ctx,ft)),"")::html_render_deep ctx r
+ | TEX_LITERAL (HTMLABLE_BIG (_,sh))::r -> (html_liberal (); ("",sh,"")::html_render_deep ctx r)
+ | TEX_FUN2h (_,f,a,b)::r -> (html_liberal (); (f a b)::html_render_deep ctx r)
+ | TEX_INFIXh (_,f,a,b)::r -> (html_liberal (); (f a b)::html_render_deep ctx r)
+ | TEX_CURLY ls::r -> html_render_deep ctx (ls @ r)
+ | TEX_DQ (a,b)::r -> (let bs = html_render_flat ctx [b] in match html_render_size ctx a with
+ true, s -> "","<font size=+2>"^s^"</font>",bs
+ | false, s -> "",(s^"<sub>"^bs^"</sub>"),"")::html_render_deep ctx r
+ | TEX_UQ (a,b)::r -> (let bs = html_render_flat ctx [b] in match html_render_size ctx a with
+ true, s -> bs,"<font size=+2>"^s^"</font>",""
+ | false, s -> "",(s^"<sup>"^bs^"</sup>"),"")::html_render_deep ctx r
+ | TEX_FQ (a,b,c)::r -> (html_liberal ();
+ (let bs = html_render_flat ctx [b] in let cs = html_render_flat ctx [c] in
+ match html_render_size ctx a with
+ true, s -> (cs,"<font size=+2>"^s^"</font>",bs)
+ | false, s -> ("",(s^"<sub>"^bs^"</sub><sup>"^cs^"</sup>"),""))::html_render_deep ctx r)
+ | TEX_FUN1hl (_,(f1,f2),a)::r -> ("",f1,"")::(html_render_deep ctx [a]) @ ("",f2,"")::html_render_deep ctx r
+ | TEX_FUN1hf (_,ff,a)::r -> (html_render_deep (new_ctx ff) [a]) @ html_render_deep ctx r
+ | TEX_DECLh (_,ff,a)::r -> (html_render_deep (new_ctx ff) a) @ html_render_deep ctx r
+ | TEX_BOX (_,s)::r -> ("",s,"")::html_render_deep ctx r
+ | TEX_LITERAL (TEX_ONLY _)::_ -> raise Too_difficult_for_html
+ | TEX_FUN1 _::_ -> raise Too_difficult_for_html
+ | TEX_FUN2 _::_ -> raise Too_difficult_for_html
+ | TEX_FUN2sq _::_ -> raise Too_difficult_for_html
+ | TEX_INFIX _::_ -> raise Too_difficult_for_html
+ | TEX_MATRIX _::_ -> raise Too_difficult_for_html
+ | TEX_LR _::_ -> raise Too_difficult_for_html
+ | TEX_BIG _::_ -> raise Too_difficult_for_html
+ | [] -> []
+
+let rec html_render_table = function
+ sf,u,d,("",a,"")::("",b,"")::r -> html_render_table (sf,u,d,(("",a^b,"")::r))
+ | sf,u,d,(("",a,"") as c)::r -> html_render_table (c::sf,u,d,r)
+ | sf,u,d,((_,a,"") as c)::r -> html_render_table (c::sf,true,d,r)
+ | sf,u,d,(("",a,_) as c)::r -> html_render_table (c::sf,u,true,r)
+ | sf,u,d,((_,a,_) as c)::r -> html_render_table (c::sf,true,true,r)
+ | sf,false,false,[] -> mapjoin (function (u,m,d) -> m) (List.rev sf)
+ | sf,true,false,[] -> let ustr,mstr = List.fold_left (fun (us,ms) (u,m,d) -> (us^"<td>"^u,ms^"<td>"^u))
+ ("","") (List.rev sf) in
+ "<table><tr align=center valign=bottom>" ^ ustr ^ "</tr><tr align=center>" ^ mstr ^ "</tr></table>"
+ | sf,false,true,[] -> let mstr,dstr = List.fold_left (fun (ms,ds) (u,m,d) -> (ms^"<td>"^m,ds^"<td>"^d))
+ ("","") (List.rev sf) in
+ "<table><tr align=center>" ^ mstr ^ "</tr><tr align=center valign=top>" ^ dstr ^ "</tr></table>"
+ | sf,true,true,[] -> let ustr,mstr,dstr = List.fold_left (fun (us,ms,ds) (u,m,d) ->
+ (us^"<td>"^u,ms^"<td>"^m,ds^"<td>"^d)) ("","","") (List.rev sf) in
+ "<table><tr align=center valign=bottom>" ^ ustr ^ "</tr><tr align=center>" ^ mstr ^ "</tr><tr align=center valign=top>" ^ dstr ^ "</tr></table>"
+
+let html_render tree = html_render_table ([],false,false,html_render_deep CTX_NORMAL tree)
+
+let render tree = try Some (html_render tree) with _ -> None
@@ -0,0 +1,5 @@
+val render : Tex.t list -> string option
+val html_render : Tex.t list -> string
+
+type conservativeness_t = CONSERVATIVE | MODERATE | LIBERAL
+val conservativeness : conservativeness_t ref
@@ -0,0 +1,90 @@
+{
+ open Parser
+ open Render_info
+ open Tex
+}
+let space = [' ' '\t' '\n' '\r']
+let alpha = ['a'-'z' 'A'-'Z']
+let literal_id = ['a'-'z' 'A'-'Z']
+let literal_mn = ['0'-'9']
+let literal_uf_lt = [',' ':' ';' '?' '!' '\'']
+let delimiter_uf_lt = ['(' ')' '.']
+let literal_uf_op = ['+' '-' '*' '=']
+let delimiter_uf_op = ['/' '|']
+let boxchars = ['0'-'9' 'a'-'z' 'A'-'Z' '+' '-' '*' ',' '=' '(' ')' ':' '/' ';' '?' '.' '!' ' ' '\128'-'\255']
+let aboxchars = ['0'-'9' 'a'-'z' 'A'-'Z' '+' '-' '*' ',' '=' '(' ')' ':' '/' ';' '?' '.' '!' ' ']
+
+rule token = parse
+ space + { token lexbuf }
+ | "\\mbox" space * '{' aboxchars + '}'
+ { let str = Lexing.lexeme lexbuf in
+ let n = String.index str '{' + 1 in
+ BOX ("\\mbox", String.sub str n (String.length str - n - 1)) }
+ | "\\hbox" space * '{' aboxchars + '}'
+ { let str = Lexing.lexeme lexbuf in
+ let n = String.index str '{' + 1 in
+ BOX ("\\hbox", String.sub str n (String.length str - n - 1)) }
+ | "\\vbox" space * '{' aboxchars + '}'
+ { let str = Lexing.lexeme lexbuf in
+ let n = String.index str '{' + 1 in
+ BOX ("\\vbox", String.sub str n (String.length str - n - 1)) }
+ | "\\mbox" space * '{' boxchars + '}'
+ { let str = Lexing.lexeme lexbuf in
+ let n = String.index str '{' + 1 in
+ Texutil.tex_use_nonascii();
+ BOX ("\\mbox", String.sub str n (String.length str - n - 1)) }
+ | "\\hbox" space * '{' boxchars + '}'
+ { let str = Lexing.lexeme lexbuf in
+ let n = String.index str '{' + 1 in
+ Texutil.tex_use_nonascii();
+ BOX ("\\hbox", String.sub str n (String.length str - n - 1)) }
+ | "\\vbox" space * '{' boxchars + '}'
+ { let str = Lexing.lexeme lexbuf in
+ let n = String.index str '{' + 1 in
+ Texutil.tex_use_nonascii();
+ BOX ("\\vbox", String.sub str n (String.length str - n - 1)) }
+ | literal_id { let str = Lexing.lexeme lexbuf in LITERAL (MHTMLABLEC (FONT_IT, str,str,MI,str)) }
+ | literal_mn { let str = Lexing.lexeme lexbuf in LITERAL (MHTMLABLEC (FONT_RM, str,str,MN,str)) }
+ | literal_uf_lt { let str = Lexing.lexeme lexbuf in LITERAL (HTMLABLEC (FONT_UFH, str,str)) }
+ | delimiter_uf_lt { let str = Lexing.lexeme lexbuf in DELIMITER (HTMLABLEC (FONT_UFH, str,str)) }
+ | literal_uf_op { let str = Lexing.lexeme lexbuf in LITERAL (MHTMLABLEC (FONT_UFH, str," "^str^" ",MO,str)) }
+ | delimiter_uf_op { let str = Lexing.lexeme lexbuf in DELIMITER (MHTMLABLEC (FONT_UFH, str," "^str^" ",MO,str)) }
+ | "\\" alpha + { Texutil.find (Lexing.lexeme lexbuf) }
+ | "\\sqrt" space * "[" { FUN_AR1opt "\\sqrt" }
+ | "\\," { LITERAL (HTMLABLE (FONT_UF, "\\,","&nbsp;")) }
+ | "\\ " { LITERAL (HTMLABLE (FONT_UF, "\\ ","&nbsp;")) }
+ | "\\;" { LITERAL (HTMLABLE (FONT_UF, "\\;","&nbsp;")) }
+ | "\\!" { LITERAL (TEX_ONLY "\\!") }
+ | "\\{" { DELIMITER (HTMLABLEC(FONT_UFH,"\\{","{")) }
+ | "\\}" { DELIMITER (HTMLABLEC(FONT_UFH,"\\}","}")) }
+ | "\\|" { DELIMITER (HTMLABLE (FONT_UFH,"\\|","||")) }
+ | "\\_" { LITERAL (HTMLABLEC(FONT_UFH,"\\_","_")) }
+ | "\\#" { LITERAL (HTMLABLE (FONT_UFH,"\\#","#")) }
+ | "\\%" { LITERAL (HTMLABLE (FONT_UFH,"\\%","%")) }
+ | "&" { NEXT_CELL }
+ | "\\\\" { NEXT_ROW }
+ | "\\begin{matrix}" { Texutil.tex_use_ams(); BEGIN__MATRIX }
+ | "\\end{matrix}" { END__MATRIX }
+ | "\\begin{pmatrix}" { Texutil.tex_use_ams(); BEGIN_PMATRIX }
+ | "\\end{pmatrix}" { END_PMATRIX }
+ | "\\begin{bmatrix}" { Texutil.tex_use_ams(); BEGIN_BMATRIX }
+ | "\\end{bmatrix}" { END_BMATRIX }
+ | "\\begin{Bmatrix}" { Texutil.tex_use_ams(); BEGIN_BBMATRIX }
+ | "\\end{Bmatrix}" { END_BBMATRIX }
+ | "\\begin{vmatrix}" { Texutil.tex_use_ams(); BEGIN_VMATRIX }
+ | "\\end{vmatrix}" { END_VMATRIX }
+ | "\\begin{Vmatrix}" { Texutil.tex_use_ams(); BEGIN_VVMATRIX }
+ | "\\end{Vmatrix}" { END_VVMATRIX }
+ | "\\begin{cases}" { Texutil.tex_use_ams(); BEGIN_CASES }
+ | "\\end{cases}" { END_CASES }
+ | '>' { LITERAL (HTMLABLEC(FONT_UFH,">"," &gt; ")) }
+ | '<' { LITERAL (HTMLABLEC(FONT_UFH,"<"," &lt; ")) }
+ | '%' { LITERAL (HTMLABLEC(FONT_UFH,"\\%","%")) }
+ | '~' { LITERAL (HTMLABLE (FONT_UF, "~","&nbsp;")) }
+ | '[' { DELIMITER (HTMLABLEC(FONT_UFH,"[","[")) }
+ | ']' { SQ_CLOSE }
+ | '{' { CURLY_OPEN }
+ | '}' { CURLY_CLOSE }
+ | '^' { SUP }
+ | '_' { SUB }
+ | eof { EOF }
@@ -0,0 +1,20 @@
+open Tex
+open Render_info
+
+type t = TREE_MN of string | TREE_MO of string | TREE_MI of string
+
+let rec make_mathml_tree = function
+ TREE_MN a::otr,TEX_LITERAL(MHTMLABLEC(_,_,_,MN,b))::itr -> make_mathml_tree(TREE_MN (a^b)::otr,itr)
+ | otr,TEX_LITERAL(MHTMLABLEC(_,_,_,MN,a))::itr -> make_mathml_tree(TREE_MN a::otr,itr)
+ | otr,TEX_LITERAL(MHTMLABLEC(_,_,_,MO,a))::itr -> make_mathml_tree(TREE_MO a::otr,itr)
+ | otr,TEX_LITERAL(MHTMLABLEC(_,_,_,MI,a))::itr -> make_mathml_tree(TREE_MI a::otr,itr)
+ | otr,TEX_CURLY(crl)::itr -> make_mathml_tree(otr,crl@itr)
+ | otr,[] -> List.rev otr
+ | _ -> failwith "failed to render mathml"
+
+let render_mathml_tree = function
+ TREE_MN s -> "<mn>"^s^"</mn>"
+ | TREE_MI s -> "<mi>"^s^"</mi>"
+ | TREE_MO s -> "<mo>"^s^"</mo>"
+
+let render tree = try Some (Util.mapjoin render_mathml_tree (make_mathml_tree ([],tree))) with _ -> None
@@ -0,0 +1 @@
+val render : Tex.t list -> string option
Oops, something went wrong.

0 comments on commit ca3a660

Please sign in to comment.