# This file is part of NIT ( http://www.nitlanguage.org ). # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. # Render commands results as HTML module html_commands import commands_catalog import commands_docdown import commands_graph import commands_ini import commands_main import commands_parser import commands_usage import templates::html_model intrude import markdown::wikilinks redef class DocCommand # Render results as a HTML string fun to_html: Writable do return "
Not yet implemented
" end redef class CmdMessage # Render the message as a HTML string fun to_html: Writable is abstract end redef class CmdError redef fun to_html do return "Error: {to_s}
" end redef class CmdWarning redef fun to_html do return "Warning: {to_s}
" end # Model commands redef class CmdEntity redef fun to_html do var mentity = self.mentity if mentity == null then return "" return mentity.html_link.write_to_string end end redef class CmdEntities redef fun to_html do var mentities = self.results if mentities == null then return "" var tpl = new Template tpl.add "{code.write_to_string}" end redef fun render_code(node) do if format == "html" then var hl = new CmdHtmlightVisitor hl.show_infobox = false hl.highlight_node node return hl.html end return super end end # Custom HtmlightVisitor for commands # # We create a new subclass so its behavior can be refined in clients without # breaking the main implementation. class CmdHtmlightVisitor super HtmlightVisitor redef fun hrefto(mentity) do if mentity isa MClassDef then return mentity.mclass.html_url if mentity isa MPropDef then return mentity.mproperty.html_url return mentity.html_url end end redef class CmdAncestors redef fun to_html do return super # FIXME lin end redef class CmdParents redef fun to_html do return super # FIXME lin end redef class CmdChildren redef fun to_html do return super # FIXME lin end redef class CmdDescendants redef fun to_html do return super # FIXME lin end redef class CmdFeatures redef fun to_html do return super # FIXME lin end redef class CmdLinearization redef fun to_html do return super # FIXME lin end # Usage commands redef class CmdNew redef fun to_html do return super # FIXME lin end redef class CmdCall redef fun to_html do return super # FIXME lin end redef class CmdReturn redef fun to_html do return super # FIXME lin end redef class CmdParam redef fun to_html do return super # FIXME lin end # Graph commands redef class CmdGraph redef fun to_html do var output = render if output == null then return "" return output.write_to_string end end # Ini commands redef class CmdIniDescription redef fun to_html do var desc = self.desc if desc == null then return "" return "
{desc}
" end end redef class CmdIniGitUrl redef fun to_html do var url = self.url if url == null then return "" return "{url}" end end redef class CmdIniCloneCommand redef fun to_html do var command = self.command if command == null then return "" return "{command}" end end redef class CmdIniIssuesUrl redef fun to_html do var url = self.url if url == null then return "" return "{url}" end end redef class CmdIniMaintainer redef fun to_html do var name = self.maintainer if name == null then return "" return "{name.html_escape}" end end redef class CmdIniContributors redef fun to_html do var names = self.contributors if names == null or names.is_empty then return "" var tpl = new Template tpl.add "
{content}" end end # Main commands redef class CmdMains redef fun to_html do return super # FIXME lin end redef class CmdMainCompile redef fun to_html do var command = self.command if command == null then return "" return "
{command}" end end redef class CmdManSynopsis redef fun to_html do var synopsis = self.synopsis if synopsis == null then return "" return "
{synopsis}" end end redef class CmdManOptions redef fun to_html do var options = self.options if options == null or options.is_empty then return "" var tpl = new Template tpl.addn "
" tpl.addn "
{opt} | " tpl.addn "{desc} | " tpl.addn "
---|
{command}" end end # MDoc # Custom Markdown processor able to process doc commands class CmdDecorator super NitdocDecorator redef type PROCESSOR: CmdMarkdownProcessor # Model used by wikilink commands to find entities var model: Model # Filter to apply if any var filter: nullable ModelFilter redef fun add_span_code(v, buffer, from, to) do var text = new FlatBuffer buffer.read(text, from, to) var name = text.write_to_string name = name.replace("nullable ", "") var mentity = try_find_mentity(name) if mentity == null then super else v.add "
"
v.emit_text mentity.html_link.write_to_string
v.add "
"
end
end
private fun try_find_mentity(text: String): nullable MEntity do
var mentity = model.mentity_by_full_name(text, filter)
if mentity != null then return mentity
var mentities = model.mentities_by_name(text, filter)
if mentities.is_empty then
return null
else if mentities.length > 1 then
# TODO smart resolve conflicts
end
return mentities.first
end
redef fun add_wikilink(v, token) do
v.render_wikilink(token, model)
end
end
# Same as `InlineDecorator` but with wikilink commands handling
class CmdInlineDecorator
super InlineDecorator
redef type PROCESSOR: CmdMarkdownProcessor
# Model used by wikilink commands to find entities
var model: Model
redef fun add_wikilink(v, token) do
v.render_wikilink(token, model)
end
end
# Custom MarkdownEmitter for commands
class CmdMarkdownProcessor
super MarkdownProcessor
# Parser used to process doc commands
var parser: CommandParser
# Render a wikilink
fun render_wikilink(token: TokenWikiLink, model: Model) do
var link = token.link
if link == null then return
var name = token.name
if name != null then link = "{name} | {link}"
var command = parser.parse(link.write_to_string)
var error = parser.error
if error isa CmdError then
emit_text error.to_html.write_to_string
return
end
if error isa CmdWarning then
emit_text error.to_html.write_to_string
end
add command.as(not null).to_html
end
end
redef class Text
# Read `self` between `nstart` and `nend` (excluded) and writte chars to `out`.
private fun read(out: FlatBuffer, nstart, nend: Int): Int do
var pos = nstart
while pos < length and pos < nend do
out.add self[pos]
pos += 1
end
if pos == length then return -1
return pos
end
end