diff options
180 files changed, 6407 insertions, 6082 deletions
@@ -25,5 +25,7 @@ TAGS .cabal-sandbox .ghc.environment.* cabal.sandbox.config +cabal.project.local +cabal.project.local~ .stack-work/ diff --git a/.travis.yml b/.travis.yml index f7a9d921..39135739 100644 --- a/.travis.yml +++ b/.travis.yml @@ -26,9 +26,9 @@ before_cache: matrix: include: - - compiler: "ghc-8.2.1" + - compiler: "ghc-8.4.2" # env: TEST=--disable-tests BENCH=--disable-benchmarks - addons: {apt: {packages: [ghc-ppa-tools,cabal-install-head,ghc-8.2.1], sources: [hvr-ghc]}} + addons: {apt: {packages: [ghc-ppa-tools,cabal-install-head,ghc-8.4.2], sources: [hvr-ghc]}} - compiler: "ghc-head" # env: TEST=--disable-tests BENCH=--disable-benchmarks addons: {apt: {packages: [ghc-ppa-tools,cabal-install-head,ghc-head], sources: [hvr-ghc]}} @@ -51,8 +51,8 @@ install: - sed -i 's/^jobs:/-- jobs:/' ${HOME}/.cabal/config - rm -fv cabal.project.local - rm -f cabal.project.freeze - - travis_retry cabal new-build -w ${HC} ${TEST} ${BENCH} --dep -j2 all - - travis_retry cabal new-build -w ${HC} --disable-tests --disable-benchmarks --dep -j2 all + - travis_retry cabal new-build -w ${HC} ${TEST} ${BENCH} --dep -j2 --allow-newer=base,Cabal --constraint 'setup.Cabal installed' all + - travis_retry cabal new-build -w ${HC} --disable-tests --disable-benchmarks --dep -j2 --allow-newer=base,Cabal --constraint 'setup.Cabal installed' all # Here starts the actual work to be performed for the package under test; # any command which exits with a non-zero exit code causes the build to fail. @@ -69,12 +69,12 @@ script: - rm -fv cabal.project.local # this builds all libraries and executables (without tests/benchmarks) - rm -f cabal.project.freeze - - cabal new-build -w ${HC} --disable-tests --disable-benchmarks all + - cabal new-build -w ${HC} --disable-tests --disable-benchmarks --allow-newer=base,Cabal --constraint 'setup.Cabal installed' all # this builds all libraries and executables (including tests/benchmarks) # - rm -rf ./dist-newstyle # build & run tests - - cabal new-build -w ${HC} ${TEST} ${BENCH} all - - if [ "x$TEST" = "x--enable-tests" ]; then cabal new-test -w ${HC} ${TEST} all; fi + - cabal new-build -w ${HC} ${TEST} ${BENCH} --allow-newer=base,Cabal --constraint 'setup.Cabal installed' all + - if [ "x$TEST" = "x--enable-tests" ]; then cabal new-test -w ${HC} ${TEST} --allow-newer=base,Cabal --constraint 'setup.Cabal installed' all; fi # EOF @@ -1,6 +1,30 @@ -## Changes in version 2.18.2 +## TBD / GHC-8.5+ - * to be released + * Overhaul handling of data declarations in XHTML and LaTeX. Adds support for + documenting individual arguments of constructors/patterns (#709) + +## Changes in version 2.20.0 + +TODO + +## Changes in version 2.19.1 + + * Show where instances are defined (#748) + + * `@since` includes package name (#452, #550, #749) + +## Changes in version 2.19.0.1 + + * Support for linking unicode operators (#458) + + * Hyperlinker: Fix file handle leak in (#763) + +## Changes in version 2.19.0 + + * Haddock now supports tables in documentation inspired by reSTs grid tables + + * `--quickjump` allows for quick navigation in documentation on hackage and + other documentation hosting sites. * A --reexport flag, which can be used to add extra modules to the top-level module tree @@ -19,11 +43,17 @@ * Fix: Generate constraint signatures for constructors exported as pattern synonyms (#663) + * The hyperlinker backend now uses the GHC lexer instead of a custom one. + This notably fixes rendering of quasiquotes. + * Overhaul Haddock's rendering of kind signatures so that invisible kind parameters are not printed (#681) (Fixes #544) - * Overhaul handling of data declarations in XHTML and LaTeX. Adds support for - documenting individual arguments of constructors/patterns (#709) + * Recognise `SPDX-License-Identifier` as alias for `License` in module header + parser (#743) + + * Remove the response file related utilities, and use the ones that + come with `base` (Trac #13896) * Remove the response file related utilities, and use the ones that come with `base` (Trac #13896) @@ -31,9 +31,9 @@ and then proceed using your favourite build tool. #### Using [`cabal new-build`](http://cabal.readthedocs.io/en/latest/nix-local-build-overview.html) ```bash -cabal new-build -w ghc-8.2.1 +cabal new-build -w ghc-8.4.1 # build & run the test suite -cabal new-test -w ghc-8.2.1 +cabal new-test -w ghc-8.4.1 ``` #### Using Cabal sandboxes diff --git a/doc/cheatsheet/haddocks.md b/doc/cheatsheet/haddocks.md index fbe71392..a3464584 100644 --- a/doc/cheatsheet/haddocks.md +++ b/doc/cheatsheet/haddocks.md @@ -118,3 +118,20 @@ definitions with "[thing]" {-# OPTIONS_HADDOCK show-extensions #-} Show all enabled LANGUAGE extensions ``` + +# Grid tables + +``` ++------------------------+------------+----------+----------+ +| Header row, column 1 | Header 2 | Header 3 | Header 4 | +| (header rows optional) | | | | ++========================+============+==========+==========+ +| body row 1, column 1 | column 2 | column 3 | column 4 | ++------------------------+------------+----------+----------+ +| body row 2 | Cells may span columns. | ++------------------------+------------+---------------------+ +| body row 3 | Cells may | \[ | ++------------------------+ span rows. | f(n) = \sum_{i=1} | +| body row 4 | | \] | ++------------------------+------------+---------------------+ +``` diff --git a/doc/markup.rst b/doc/markup.rst index 4d56cc83..1a278da3 100644 --- a/doc/markup.rst +++ b/doc/markup.rst @@ -1092,6 +1092,26 @@ If the output format supports it, the mathematics will be rendered inside the documentation. For example, the HTML backend will display the mathematics via `MathJax <https://www.mathjax.org>`__. +Grid Tables +~~~~~~~~~~~ + +Inspired by reSTs grid tables Haddock supports a complete table representation via a grid-like "ASCII art". Grid tables are described with a visual grid made up of the characters "-", "=", "|", and "+". The hyphen ("-") is used for horizontal lines (row separators). The equals sign ("=") may be used to separate optional header rows from the table body. The vertical bar ("|") is used for vertical lines (column separators). The plus sign ("+") is used for intersections of horizontal and vertical lines. :: + + -- | This is a grid table: + -- + -- +------------------------+------------+----------+----------+ + -- | Header row, column 1 | Header 2 | Header 3 | Header 4 | + -- | (header rows optional) | | | | + -- +========================+============+==========+==========+ + -- | body row 1, column 1 | column 2 | column 3 | column 4 | + -- +------------------------+------------+----------+----------+ + -- | body row 2 | Cells may span columns. | + -- +------------------------+------------+---------------------+ + -- | body row 3 | Cells may | \[ | + -- +------------------------+ span rows. | f(n) = \sum_{i=1} | + -- | body row 4 | | \] | + -- +------------------------+------------+---------------------+ + Anchors ~~~~~~~ diff --git a/haddock-api/haddock-api.cabal b/haddock-api/haddock-api.cabal index 0aac70e5..3e972877 100644 --- a/haddock-api/haddock-api.cabal +++ b/haddock-api/haddock-api.cabal @@ -1,5 +1,6 @@ +cabal-version: 2.0 name: haddock-api -version: 2.18.2 +version: 2.20.0 synopsis: A documentation-generation tool for Haskell libraries description: Haddock is a documentation-generation tool for Haskell libraries @@ -12,7 +13,6 @@ bug-reports: https://github.com/haskell/haddock/issues copyright: (c) Simon Marlow, David Waern category: Documentation build-type: Simple -cabal-version: >= 2.0 extra-source-files: CHANGES.md @@ -41,10 +41,10 @@ library -- this package typically supports only single major versions build-depends: base ^>= 4.12.0 - , Cabal ^>= 2.0.0 - , ghc ^>= 8.3 + , Cabal ^>= 2.3.0 + , ghc ^>= 8.5 , ghc-paths ^>= 0.1.0.9 - , haddock-library ^>= 1.4.6 + , haddock-library ^>= 1.6.0 , xhtml ^>= 3000.2.2 -- Versions for the dependencies below are transitively pinned by @@ -124,27 +124,71 @@ test-suite spec test , src - -- NB: We only use a small subset of lib:haddock-api here, which - -- explains why this component has a smaller build-depends set other-modules: + Haddock + Haddock.Backends.Hoogle + Haddock.Backends.Hyperlinker + Haddock.Backends.Hyperlinker.Ast + Haddock.Backends.Hyperlinker.Renderer + Haddock.Backends.Hyperlinker.Utils + Haddock.Backends.LaTeX + Haddock.Backends.Xhtml + Haddock.Backends.Xhtml.Decl + Haddock.Backends.Xhtml.DocMarkup + Haddock.Backends.Xhtml.Layout + Haddock.Backends.Xhtml.Meta + Haddock.Backends.Xhtml.Names + Haddock.Backends.Xhtml.Themes + Haddock.Backends.Xhtml.Types + Haddock.Backends.Xhtml.Utils + Haddock.Convert + Haddock.Doc + Haddock.GhcUtils + Haddock.Interface + Haddock.Interface.AttachInstances + Haddock.Interface.Create + Haddock.Interface.Json + Haddock.Interface.LexParseRn + Haddock.Interface.ParseModuleHeader + Haddock.Interface.Rename + Haddock.Interface.Specialize + Haddock.InterfaceFile + Haddock.ModuleTree + Haddock.Options + Haddock.Parser + Haddock.Syb + Haddock.Types + Haddock.Utils + Haddock.Utils.Json + Haddock.Version + Paths_haddock_api Haddock.Backends.Hyperlinker.ParserSpec Haddock.Backends.Hyperlinker.Parser Haddock.Backends.Hyperlinker.Types - build-depends: - ghc ^>= 8.3 - , hspec ^>= 2.4.4 - , QuickCheck ^>= 2.10 + build-depends: Cabal ^>= 2.3 + , ghc ^>= 8.4 + , ghc-paths ^>= 0.1.0.9 + , haddock-library ^>= 1.6.0 + , xhtml ^>= 3000.2.2 + , hspec >= 2.4.4 && < 2.6 + , QuickCheck ^>= 2.11 -- Versions for the dependencies below are transitively pinned by -- the non-reinstallable `ghc` package and hence need no version -- bounds - build-depends: - base - , containers + build-depends: base + , array + , bytestring + , containers + , deepseq + , directory + , filepath + , ghc-boot + , transformers build-tool-depends: - hspec-discover:hspec-discover ^>= 2.4.4 + hspec-discover:hspec-discover >= 2.4.4 && < 2.6 source-repository head type: git diff --git a/haddock-api/resources/html/Classic.theme/xhaddock.css b/haddock-api/resources/html/Classic.theme/xhaddock.css index 1bf668e9..b8164815 100644 --- a/haddock-api/resources/html/Classic.theme/xhaddock.css +++ b/haddock-api/resources/html/Classic.theme/xhaddock.css @@ -392,6 +392,20 @@ td.rdoc p { } +.doc table { + border-collapse: collapse; + border-spacing: 0px; +} + +.doc th, +.doc td { + padding: 5px; + border: 1px solid #ddd; +} + +.doc th { + background-color: #f0f0f0; +} #footer { background-color: #000099; diff --git a/haddock-api/resources/html/Ocean.std-theme/ocean.css b/haddock-api/resources/html/Ocean.std-theme/ocean.css index 0852dea5..ba6af9ca 100644 --- a/haddock-api/resources/html/Ocean.std-theme/ocean.css +++ b/haddock-api/resources/html/Ocean.std-theme/ocean.css @@ -443,6 +443,21 @@ div#style-menu-holder { margin-top: 0.8em; } +.doc table { + border-collapse: collapse; + border-spacing: 0px; +} + +.doc th, +.doc td { + padding: 5px; + border: 1px solid #ddd; +} + +.doc th { + background-color: #f0f0f0; +} + .clearfix:after { clear: both; content: " "; diff --git a/haddock-api/resources/html/haddock-bundle.min.js b/haddock-api/resources/html/haddock-bundle.min.js index 82a34ddb..1061714b 100644 --- a/haddock-api/resources/html/haddock-bundle.min.js +++ b/haddock-api/resources/html/haddock-bundle.min.js @@ -1,2 +1,2 @@ -!function e(t,n,o){function r(s,a){if(!n[s]){if(!t[s]){var l="function"==typeof require&&require;if(!a&&l)return l(s,!0);if(i)return i(s,!0);var c=new Error("Cannot find module '"+s+"'");throw c.code="MODULE_NOT_FOUND",c}var u=n[s]={exports:{}};t[s][0].call(u.exports,function(e){var n=t[s][1][e];return r(n||e)},u,u.exports,e,t,n,o)}return n[s].exports}for(var i="function"==typeof require&&require,s=0;s<o.length;s++)r(o[s]);return r}({1:[function(e,t,n){"use strict";Object.defineProperty(n,"__esModule",{value:!0}),n.setCookie=function(e,t){document.cookie=e+"="+encodeURIComponent(t)+";path=/;"},n.clearCookie=function(e){document.cookie=e+"=;path=/;expires=Thu, 01-Jan-1970 00:00:01 GMT;"},n.getCookie=function(e){for(var t=e+"=",n=document.cookie.split(";"),o=0;o<n.length;o++){for(var r=n[o];" "==r.charAt(0);)r=r.substring(1,r.length);if(0==r.indexOf(t))return decodeURIComponent(r.substring(t.length,r.length))}return null}},{}],2:[function(e,t,n){"use strict";function o(e){var t=d[e];if(void 0==t)throw new Error("could not find <details> element with id '"+e+"'");return t}function r(e){for(var t=e.target,n=t.id,r=o(n),i=r.element.open,s=0,l=r.toggles;s<l.length;s++){var c=l[s];c.classList.contains("details-toggle-control")&&(c.classList.add(i?"collapser":"expander"),c.classList.remove(i?"expander":"collapser"))}t.open==r.openByDefault?delete p[n]:p[n]=!0,a()}function i(){for(var e=0,t=Array.prototype.slice.call(document.getElementsByTagName("details"));e<t.length;e++){var n=t[e];"string"==typeof n.id&&n.id.length>0&&(d[n.id]={element:n,openByDefault:!!n.open,toggles:[]},n.addEventListener("toggle",r))}}function s(e){var t=o(e).element;t.open=!t.open}function a(){var e=Object.keys(p);document.cookie="toggled="+encodeURIComponent(e.join("+"))}function l(){var e=h.getCookie("toggled");if(e)for(var t=0,n=e.split("+");t<n.length;t++){var o=n[t],r=d[o];p[o]=!0,r&&(r.element.open=!r.element.open)}}function c(e){e.preventDefault();var t=e.currentTarget.getAttribute("data-details-id");if(!t)throw new Error("element with class 'details-toggle' has no 'data-details-id' attribute!");s(t)}function u(){Array.prototype.slice.call(document.getElementsByClassName("details-toggle")).forEach(function(e){var t=e.getAttribute("data-details-id");if(!t)throw new Error("element with class 'details-toggle' has no 'data-details-id' attribute!");var n=o(t);n.toggles.push(e),e.addEventListener("click",c),e.classList.contains("details-toggle-control")&&e.classList.add(n.element.open?"collapser":"expander")})}Object.defineProperty(n,"__esModule",{value:!0});var h=e("./cookies"),d={},p={};n.init=function(){i(),l(),u()}},{"./cookies":1}],3:[function(e,t,n){"use strict";Object.defineProperty(n,"__esModule",{value:!0});var o=e("./style-menu"),r=e("./details-helper"),i=e("./quick-jump");!function(e){"interactive"===document.readyState?e():document.addEventListener("readystatechange",function(){"interactive"===document.readyState&&e()})}(function(){document.body.classList.add("js-enabled"),o.init(),r.init(),i.init()})},{"./details-helper":2,"./quick-jump":4,"./style-menu":5}],4:[function(e,t,n){"use strict";function o(e,t,n){var o=new XMLHttpRequest;o.onreadystatechange=function(){if(o.readyState===XMLHttpRequest.DONE)if(200===o.status){if(t)try{t(JSON.parse(o.responseText))}catch(e){n(o)}}else n&&n(o)},o.open("GET",e,!0),o.send()}function r(e){var t=document.querySelector("#page-menu"),n=document.createElement("li");t.insertBefore(n,t.firstChild),d.render(p(v,{onClick:e,title:"Quick Jump"}),t,n)}function i(e,t){return t.length<=e?t:t.slice(0,e)}function s(){return p("table",{class:"keyboard-shortcuts"},p("tr",null,p("th",null,"Key"),p("th",null,"Shortcut")),p("tr",null,p("td",null,p("span",{class:"key"},"s")),p("td",null,"Open this search box")),p("tr",null,p("td",null,p("span",{class:"key"},"esc")),p("td",null,"Close this search box")),p("tr",null,p("td",null,p("span",{class:"key"},"↓"),",",p("span",{class:"key"},"ctrl")," + ",p("span",{class:"key"},"j")),p("td",null,"Move down in search results")),p("tr",null,p("td",null,p("span",{class:"key"},"↑"),",",p("span",{class:"key"},"ctrl")," + ",p("span",{class:"key"},"k")),p("td",null,"Move up in search results")),p("tr",null,p("td",null,p("span",{class:"key"},"↵")),p("td",null,"Go to active search result")))}function a(){return p("p",null,"You can find any exported type, constructor, class, function or pattern defined in this package by (approximate) name.")}function l(e){var t=[p("p",null,"Your search for '",e.searchString,"' produced the following list of results: ",p("code",null,"[]"),"."),p("p",null,p("code",null,"Nothing")," matches your query for '",e.searchString,"'."),p("p",null,p("code",null,"Left \"no matches for '",e.searchString,"'\" :: Either String (NonEmpty SearchResult)"))];return t[(e.searchString||"a").charCodeAt(0)%t.length]}function c(e,t){d.render(p(g,{baseUrl:e||".",showHideTrigger:t||r}),document.body)}var u=this&&this.__extends||function(){var e=Object.setPrototypeOf||{__proto__:[]}instanceof Array&&function(e,t){e.__proto__=t}||function(e,t){for(var n in t)t.hasOwnProperty(n)&&(e[n]=t[n])};return function(t,n){function o(){this.constructor=t}e(t,n),t.prototype=null===n?Object.create(n):(o.prototype=n.prototype,new o)}}();Object.defineProperty(n,"__esModule",{value:!0});var h=e("fuse.js"),d=e("preact"),p=d.h,f=d.Component,v=function(e){function t(){return null!==e&&e.apply(this,arguments)||this}return u(t,e),t.prototype.render=function(e){return p("li",null,p("a",{href:"#",onClick:function(t){t.preventDefault(),e.onClick()}},e.title))},t}(f),g=function(e){function t(){var t=null!==e&&e.apply(this,arguments)||this;return t.linkIndex=0,t.focusPlease=!1,t.navigatedByKeyboard=!1,t}return u(t,e),t.prototype.componentWillMount=function(){var e=this;this.setState({searchString:"",isVisible:!1,expanded:{},activeLinkIndex:-1,moduleResults:[]}),o(this.props.baseUrl+"/doc-index.json",function(t){e.setState({fuse:new h(t,{threshold:.25,caseSensitive:!0,includeScore:!0,tokenize:!0,keys:["name","module"]}),moduleResults:[]})},function(t){console&&console.error("could not load 'doc-index.json' for searching",t),e.setState({failedLoading:!0})}),document.addEventListener("mousedown",this.hide.bind(this)),document.addEventListener("keydown",function(t){e.state.isVisible&&("Escape"===t.key?e.hide():"ArrowUp"===t.key||"k"===t.key&&t.ctrlKey?(t.preventDefault(),e.navigateLinks(-1)):"ArrowDown"===t.key||"j"===t.key&&t.ctrlKey?(t.preventDefault(),e.navigateLinks(1)):"Enter"===t.key&&e.state.activeLinkIndex>=0&&e.followActiveLink()),"s"===t.key&&"input"!==t.target.tagName.toLowerCase()&&(t.preventDefault(),e.show())})},t.prototype.hide=function(){this.setState({isVisible:!1})},t.prototype.show=function(){this.state.isVisible||(this.focusPlease=!0,this.setState({isVisible:!0,activeLinkIndex:-1}))},t.prototype.toggleVisibility=function(){this.state.isVisible?this.hide():this.show()},t.prototype.navigateLinks=function(e){var t=Math.max(-1,Math.min(this.linkIndex-1,this.state.activeLinkIndex+e));this.navigatedByKeyboard=!0,this.setState({activeLinkIndex:t})},t.prototype.followActiveLink=function(){this.activeLinkAction&&this.activeLinkAction()},t.prototype.updateResults=function(){var e=this.input&&this.input.value||"",t={};this.state.fuse.search(e).forEach(function(e){var n=e.item.module;(t[n]||(t[n]=[])).push(e)});var n=[];for(var o in t)!function(e){var o=t[e],r=0;o.forEach(function(e){r+=1/e.score}),n.push({module:e,totalScore:1/r,items:o})}(o);n.sort(function(e,t){return e.totalScore-t.totalScore}),this.setState({searchString:e,isVisible:!0,moduleResults:n})},t.prototype.componentDidUpdate=function(){if(this.searchResults&&this.activeLink&&this.navigatedByKeyboard){var e=this.activeLink.getClientRects()[0],t=this.searchResults.getClientRects()[0].top;e.bottom>window.innerHeight?this.searchResults.scrollTop+=e.bottom-window.innerHeight+80:e.top<t&&(this.searchResults.scrollTop-=t-e.top+80)}this.focusPlease&&this.input&&this.input.focus(),this.navigatedByKeyboard=!1,this.focusPlease=!1},t.prototype.componentDidMount=function(){this.props.showHideTrigger(this.toggleVisibility.bind(this))},t.prototype.render=function(e,t){var n=this;if(t.failedLoading){var o="file:"==window.location.protocol;return p("div",{id:"search",class:t.isVisible?"":"hidden"},p("div",{id:"search-results"},p("p",{class:"error"},"Failed to load file 'doc-index.json' containing definitions in this package."),o?p("p",{class:"error"},"To use quick jump, load this page with HTTP (from a local static file web server) instead of using the ",p("code",null,"file://")," protocol. (For security reasons, it is not possible to fetch auxiliary files using JS in a HTML page opened with ",p("code",null,"file://"),".)"):[]))}this.linkIndex=0;var r=function(e){e.stopPropagation()},c=i(10,t.moduleResults).map(function(e){return n.renderResultsInModule(e)});return p("div",{id:"search",class:t.isVisible?"":"hidden"},p("div",{id:"search-form",onMouseDown:r},p("input",{placeholder:"Search in package by name",ref:function(e){n.input=e},onFocus:this.show.bind(this),onClick:this.show.bind(this),onInput:this.updateResults.bind(this)})),p("div",{id:"search-results",ref:function(e){n.searchResults=e},onMouseDown:r,onMouseOver:function(e){for(var t=e.target;t&&"function"==typeof t.getAttribute;){var o=t.getAttribute("data-link-index");if("string"==typeof o){var r=parseInt(o,10);n.setState({activeLinkIndex:r});break}t=t.parentNode}}},""===t.searchString?[p(a,null),p(s,null)]:0==c.length?p(l,{searchString:t.searchString}):p("ul",null,c)))},t.prototype.renderResultsInModule=function(e){var t=this,n=e.items,o=e.module,r=this.state.expanded[o]||n.length<=10,s=r?n:i(8,n),a=function(e){return p("li",{class:"search-result"},t.navigationLink(t.props.baseUrl+"/"+e.link,{},p(m,{html:e.display_html})))};return p("li",{class:"search-module"},p("h4",null,o),p("ul",null,s.map(function(e){return a(e.item)}),r?[]:p("li",{class:"more-results"},this.actionLink(function(){var e=Object.assign({},t.state.expanded);e[o]=!0,t.setState({expanded:e})},{},"show "+(n.length-s.length)+" more results from this module"))))},t.prototype.navigationLink=function(e,t){for(var n=this,o=[],r=2;r<arguments.length;r++)o[r-2]=arguments[r];var i=Object.assign({href:e,onClick:this.hide.bind(this)},t),s=function(){window.location.href=e,n.hide()};return this.menuLink.apply(this,[i,s].concat(o))},t.prototype.actionLink=function(e,t){for(var n=[],o=2;o<arguments.length;o++)n[o-2]=arguments[o];var r=Object.assign({href:"#",onClick:function(t){t.preventDefault(),e()}},t);return this.menuLink.apply(this,[r,e].concat(n))},t.prototype.menuLink=function(e,t){for(var n=this,o=[],r=2;r<arguments.length;r++)o[r-2]=arguments[r];var i=this.linkIndex;i===this.state.activeLinkIndex&&(e.class=(e.class?e.class+" ":"")+"active-link",e.ref=function(e){e&&(n.activeLink=e)},this.activeLinkAction=t);var s=Object.assign({"data-link-index":i},e);return this.linkIndex+=1,p.apply(void 0,["a",s].concat(o))},t}(f),m=function(e){function t(){return null!==e&&e.apply(this,arguments)||this}return u(t,e),t.prototype.shouldComponentUpdate=function(e){return this.props.html!==e.html},t.prototype.render=function(e){return p("div",{dangerouslySetInnerHTML:{__html:e.html}})},t}(f);n.init=c,window.quickNav={init:c}},{"fuse.js":6,preact:7}],5:[function(e,t,n){"use strict";function o(e){return(" "+e+" ").replace(g," ")}function r(e){return e.replace(m,"")}function i(e,t){return o(e.className||"").indexOf(" "+t+" ")>=0}function s(e,t){var n=o(e.className||"");n.indexOf(" "+t+" ")<0&&(e.className=r(n+" "+t))}function a(e,t){var n=o(e.className||"");n=n.replace(" "+t+" "," "),e.className=r(n)}function l(e,t,n,o){return null==o&&(o=!i(e,t)),o?(a(e,n),s(e,t)):(a(e,t),s(e,n)),o}function c(e){var t=document.getElementById("page-menu");if(t&&t.firstChild){var n=t.firstChild.cloneNode(!1);n.innerHTML=e,t.appendChild(n)}}function u(){return Array.prototype.slice.call(document.getElementsByTagName("link")).filter(function(e){return-1!=e.rel.indexOf("style")&&e.title})}function h(){var e=u(),t="";e.forEach(function(e){t+="<li><a href='#' onclick=\"setActiveStyleSheet('"+e.title+"'); return false;\">"+e.title+"</a></li>"}),e.length>1&&c("<div id='style-menu-holder'><a href='#' onclick='styleMenu(); return false;'>Style ▾</a><ul id='style-menu' class='hide'>"+t+"</ul></div>")}function d(e){for(var t=u(),n=null,o=0;o<t.length;o++){var r=t[o];r.disabled=!0,r.title==e&&(n=r)}n?(n.disabled=!1,v.setCookie("haddock-style",e)):(t[0].disabled=!1,v.clearCookie("haddock-style")),f(!1)}function p(){var e=v.getCookie("haddock-style");e&&d(e)}function f(e){var t=document.getElementById("style-menu");t&&y(t,e)}Object.defineProperty(n,"__esModule",{value:!0});var v=e("./cookies"),g=/\s\s+/g,m=/^\s+|\s+$/g,y=function(e,t){return function(n,o){return l(n,e,t,o)}}("show","hide");n.init=function(){h(),p()}},{"./cookies":1}],6:[function(e,t,n){!function(e,o){"object"==typeof n&&"object"==typeof t?t.exports=o():"function"==typeof define&&define.amd?define("Fuse",[],o):"object"==typeof n?n.Fuse=o():e.Fuse=o()}(this,function(){return function(e){function t(o){if(n[o])return n[o].exports;var r=n[o]={i:o,l:!1,exports:{}};return e[o].call(r.exports,r,r.exports,t),r.l=!0,r.exports}var n={};return t.m=e,t.c=n,t.i=function(e){return e},t.d=function(e,n,o){t.o(e,n)||Object.defineProperty(e,n,{configurable:!1,enumerable:!0,get:o})},t.n=function(e){var n=e&&e.__esModule?function(){return e.default}:function(){return e};return t.d(n,"a",n),n},t.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},t.p="",t(t.s=8)}([function(e,t,n){"use strict";e.exports=function(e){return"[object Array]"===Object.prototype.toString.call(e)}},function(e,t,n){"use strict";function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}var r=function(){function e(e,t){for(var n=0;n<t.length;n++){var o=t[n];o.enumerable=o.enumerable||!1,o.configurable=!0,"value"in o&&(o.writable=!0),Object.defineProperty(e,o.key,o)}}return function(t,n,o){return n&&e(t.prototype,n),o&&e(t,o),t}}(),i=n(5),s=n(7),a=n(4),l=function(){function e(t,n){var r=n.location,i=void 0===r?0:r,s=n.distance,l=void 0===s?100:s,c=n.threshold,u=void 0===c?.6:c,h=n.maxPatternLength,d=void 0===h?32:h,p=n.isCaseSensitive,f=void 0!==p&&p,v=n.tokenSeparator,g=void 0===v?/ +/g:v,m=n.findAllMatches,y=void 0!==m&&m,_=n.minMatchCharLength,k=void 0===_?1:_;o(this,e),this.options={location:i,distance:l,threshold:u,maxPatternLength:d,isCaseSensitive:f,tokenSeparator:g,findAllMatches:y,minMatchCharLength:k},this.pattern=this.options.isCaseSensitive?t:t.toLowerCase(),this.pattern.length<=d&&(this.patternAlphabet=a(this.pattern))}return r(e,[{key:"search",value:function(e){if(this.options.isCaseSensitive||(e=e.toLowerCase()),this.pattern===e)return{isMatch:!0,score:0,matchedIndices:[[0,e.length-1]]};var t=this.options,n=t.maxPatternLength,o=t.tokenSeparator;if(this.pattern.length>n)return i(e,this.pattern,o);var r=this.options,a=r.location,l=r.distance,c=r.threshold,u=r.findAllMatches,h=r.minMatchCharLength;return s(e,this.pattern,this.patternAlphabet,{location:a,distance:l,threshold:c,findAllMatches:u,minMatchCharLength:h})}}]),e}();e.exports=l},function(e,t,n){"use strict";var o=n(0),r=function e(t,n,r){if(n){var i=n.indexOf("."),s=n,a=null;-1!==i&&(s=n.slice(0,i),a=n.slice(i+1));var l=t[s];if(null!==l&&void 0!==l)if(a||"string"!=typeof l&&"number"!=typeof l)if(o(l))for(var c=0,u=l.length;c<u;c+=1)e(l[c],a,r);else a&&e(l,a,r);else r.push(l.toString())}else r.push(t);return r};e.exports=function(e,t){return r(e,t,[])}},function(e,t,n){"use strict";e.exports=function(){for(var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:[],t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:1,n=[],o=-1,r=-1,i=0,s=e.length;i<s;i+=1){var a=e[i];a&&-1===o?o=i:a||-1===o||((r=i-1)-o+1>=t&&n.push([o,r]),o=-1)}return e[i-1]&&i-o>=t&&n.push([o,i-1]),n}},function(e,t,n){"use strict";e.exports=function(e){for(var t={},n=e.length,o=0;o<n;o+=1)t[e.charAt(o)]=0;for(var r=0;r<n;r+=1)t[e.charAt(r)]|=1<<n-r-1;return t}},function(e,t,n){"use strict";var o=/[\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|]/g;e.exports=function(e,t){var n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:/ +/g,r=new RegExp(t.replace(o,"\\$&").replace(n,"|")),i=e.match(r),s=!!i,a=[];if(s)for(var l=0,c=i.length;l<c;l+=1){var u=i[l];a.push([e.indexOf(u),u.length-1])}return{score:s?.5:1,isMatch:s,matchedIndices:a}}},function(e,t,n){"use strict";e.exports=function(e,t){var n=t.errors,o=void 0===n?0:n,r=t.currentLocation,i=void 0===r?0:r,s=t.expectedLocation,a=void 0===s?0:s,l=t.distance,c=void 0===l?100:l,u=o/e.length,h=Math.abs(a-i);return c?u+h/c:h?1:u}},function(e,t,n){"use strict";var o=n(6),r=n(3);e.exports=function(e,t,n,i){for(var s=i.location,a=void 0===s?0:s,l=i.distance,c=void 0===l?100:l,u=i.threshold,h=void 0===u?.6:u,d=i.findAllMatches,p=void 0!==d&&d,f=i.minMatchCharLength,v=void 0===f?1:f,g=a,m=e.length,y=h,_=e.indexOf(t,g),k=t.length,b=[],x=0;x<m;x+=1)b[x]=0;if(-1!==_){var w=o(t,{errors:0,currentLocation:_,expectedLocation:g,distance:c});if(y=Math.min(w,y),-1!==(_=e.lastIndexOf(t,g+k))){var S=o(t,{errors:0,currentLocation:_,expectedLocation:g,distance:c});y=Math.min(S,y)}}_=-1;for(var L=[],C=1,M=k+m,N=1<<k-1,I=0;I<k;I+=1){for(var A=0,O=M;A<O;)o(t,{errors:I,currentLocation:g+O,expectedLocation:g,distance:c})<=y?A=O:M=O,O=Math.floor((M-A)/2+A);M=O;var E=Math.max(1,g-O+1),T=p?m:Math.min(g+O,m)+k,j=Array(T+2);j[T+1]=(1<<I)-1;for(var P=T;P>=E;P-=1){var R=P-1,U=n[e.charAt(R)];if(U&&(b[R]=1),j[P]=(j[P+1]<<1|1)&U,0!==I&&(j[P]|=(L[P+1]|L[P])<<1|1|L[P+1]),j[P]&N&&(C=o(t,{errors:I,currentLocation:R,expectedLocation:g,distance:c}))<=y){if(y=C,(_=R)<=g)break;E=Math.max(1,2*g-_)}}if(o(t,{errors:I+1,currentLocation:g,expectedLocation:g,distance:c})>y)break;L=j}return{isMatch:_>=0,score:0===C?.001:C,matchedIndices:r(b,v)}}},function(e,t,n){"use strict";function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}var r=function(){function e(e,t){for(var n=0;n<t.length;n++){var o=t[n];o.enumerable=o.enumerable||!1,o.configurable=!0,"value"in o&&(o.writable=!0),Object.defineProperty(e,o.key,o)}}return function(t,n,o){return n&&e(t.prototype,n),o&&e(t,o),t}}(),i=n(1),s=n(2),a=n(0),l=function(){function e(t,n){var r=n.location,i=void 0===r?0:r,a=n.distance,l=void 0===a?100:a,c=n.threshold,u=void 0===c?.6:c,h=n.maxPatternLength,d=void 0===h?32:h,p=n.caseSensitive,f=void 0!==p&&p,v=n.tokenSeparator,g=void 0===v?/ +/g:v,m=n.findAllMatches,y=void 0!==m&&m,_=n.minMatchCharLength,k=void 0===_?1:_,b=n.id,x=void 0===b?null:b,w=n.keys,S=void 0===w?[]:w,L=n.shouldSort,C=void 0===L||L,M=n.getFn,N=void 0===M?s:M,I=n.sortFn,A=void 0===I?function(e,t){return e.score-t.score}:I,O=n.tokenize,E=void 0!==O&&O,T=n.matchAllTokens,j=void 0!==T&&T,P=n.includeMatches,R=void 0!==P&&P,U=n.includeScore,D=void 0!==U&&U,V=n.verbose,F=void 0!==V&&V;o(this,e),this.options={location:i,distance:l,threshold:u,maxPatternLength:d,isCaseSensitive:f,tokenSeparator:g,findAllMatches:y,minMatchCharLength:k,id:x,keys:S,includeMatches:R,includeScore:D,shouldSort:C,getFn:N,sortFn:A,verbose:F,tokenize:E,matchAllTokens:j},this.setCollection(t)}return r(e,[{key:"setCollection",value:function(e){return this.list=e,e}},{key:"search",value:function(e){this._log('---------\nSearch pattern: "'+e+'"');var t=this._prepareSearchers(e),n=t.tokenSearchers,o=t.fullSearcher,r=this._search(n,o),i=r.weights,s=r.results;return this._computeScore(i,s),this.options.shouldSort&&this._sort(s),this._format(s)}},{key:"_prepareSearchers",value:function(){var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:"",t=[];if(this.options.tokenize)for(var n=e.split(this.options.tokenSeparator),o=0,r=n.length;o<r;o+=1)t.push(new i(n[o],this.options));return{tokenSearchers:t,fullSearcher:new i(e,this.options)}}},{key:"_search",value:function(){var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:[],t=arguments[1],n=this.list,o={},r=[];if("string"==typeof n[0]){for(var i=0,s=n.length;i<s;i+=1)this._analyze({key:"",value:n[i],record:i,index:i},{resultMap:o,results:r,tokenSearchers:e,fullSearcher:t});return{weights:null,results:r}}for(var a={},l=0,c=n.length;l<c;l+=1)for(var u=n[l],h=0,d=this.options.keys.length;h<d;h+=1){var p=this.options.keys[h];if("string"!=typeof p){if(a[p.name]={weight:1-p.weight||1},p.weight<=0||p.weight>1)throw new Error("Key weight has to be > 0 and <= 1");p=p.name}else a[p]={weight:1};this._analyze({key:p,value:this.options.getFn(u,p),record:u,index:l},{resultMap:o,results:r,tokenSearchers:e,fullSearcher:t})}return{weights:a,results:r}}},{key:"_analyze",value:function(e,t){var n=e.key,o=e.arrayIndex,r=void 0===o?-1:o,i=e.value,s=e.record,l=e.index,c=t.tokenSearchers,u=void 0===c?[]:c,h=t.fullSearcher,d=void 0===h?[]:h,p=t.resultMap,f=void 0===p?{}:p,v=t.results,g=void 0===v?[]:v;if(void 0!==i&&null!==i){var m=!1,y=-1,_=0;if("string"==typeof i){this._log("\nKey: "+(""===n?"-":n));var k=d.search(i);if(this._log('Full text: "'+i+'", score: '+k.score),this.options.tokenize){for(var b=i.split(this.options.tokenSeparator),x=[],w=0;w<u.length;w+=1){var S=u[w];this._log('\nPattern: "'+S.pattern+'"');for(var L=!1,C=0;C<b.length;C+=1){var M=b[C],N=S.search(M),I={};N.isMatch?(I[M]=N.score,m=!0,L=!0,x.push(N.score)):(I[M]=1,this.options.matchAllTokens||x.push(1)),this._log('Token: "'+M+'", score: '+I[M])}L&&(_+=1)}y=x[0];for(var A=x.length,O=1;O<A;O+=1)y+=x[O];y/=A,this._log("Token score average:",y)}var E=k.score;y>-1&&(E=(E+y)/2),this._log("Score average:",E);var T=!this.options.tokenize||!this.options.matchAllTokens||_>=u.length;if(this._log("\nCheck Matches: "+T),(m||k.isMatch)&&T){var j=f[l];j?j.output.push({key:n,arrayIndex:r,value:i,score:E,matchedIndices:k.matchedIndices}):(f[l]={item:s,output:[{key:n,arrayIndex:r,value:i,score:E,matchedIndices:k.matchedIndices}]},g.push(f[l]))}}else if(a(i))for(var P=0,R=i.length;P<R;P+=1)this._analyze({key:n,arrayIndex:P,value:i[P],record:s,index:l},{resultMap:f,results:g,tokenSearchers:u,fullSearcher:d})}}},{key:"_computeScore",value:function(e,t){this._log("\n\nComputing score:\n");for(var n=0,o=t.length;n<o;n+=1){for(var r=t[n].output,i=r.length,s=0,a=1,l=0;l<i;l+=1){var c=e?e[r[l].key].weight:1,u=(1===c?r[l].score:r[l].score||.001)*c;1!==c?a=Math.min(a,u):(r[l].nScore=u,s+=u)}t[n].score=1===a?s/i:a,this._log(t[n])}}},{key:"_sort",value:function(e){this._log("\n\nSorting...."),e.sort(this.options.sortFn)}},{key:"_format",value:function(e){var t=[];this._log("\n\nOutput:\n\n",JSON.stringify(e));var n=[];this.options.includeMatches&&n.push(function(e,t){var n=e.output;t.matches=[];for(var o=0,r=n.length;o<r;o+=1){var i=n[o];if(0!==i.matchedIndices.length){var s={indices:i.matchedIndices,value:i.value};i.key&&(s.key=i.key),i.hasOwnProperty("arrayIndex")&&i.arrayIndex>-1&&(s.arrayIndex=i.arrayIndex),t.matches.push(s)}}}),this.options.includeScore&&n.push(function(e,t){t.score=e.score});for(var o=0,r=e.length;o<r;o+=1){var i=e[o];if(this.options.id&&(i.item=this.options.getFn(i.item,this.options.id)[0]),n.length){for(var s={item:i.item},a=0,l=n.length;a<l;a+=1)n[a](i,s);t.push(s)}else t.push(i.item)}return t}},{key:"_log",value:function(){if(this.options.verbose){var e;(e=console).log.apply(e,arguments)}}}]),e}();e.exports=l}])})},{}],7:[function(e,t,n){!function(){"use strict";function e(){}function n(t,n){var o,r,i,s,a=O;for(s=arguments.length;s-- >2;)A.push(arguments[s]);for(n&&null!=n.children&&(A.length||A.push(n.children),delete n.children);A.length;)if((r=A.pop())&&void 0!==r.pop)for(s=r.length;s--;)A.push(r[s]);else"boolean"==typeof r&&(r=null),(i="function"!=typeof t)&&(null==r?r="":"number"==typeof r?r=String(r):"string"!=typeof r&&(i=!1)),i&&o?a[a.length-1]+=r:a===O?a=[r]:a.push(r),o=i;var l=new e;return l.nodeName=t,l.children=a,l.attributes=null==n?void 0:n,l.key=null==n?void 0:n.key,void 0!==I.vnode&&I.vnode(l),l}function o(e,t){for(var n in t)e[n]=t[n];return e}function r(e){!e.__d&&(e.__d=!0)&&1==j.push(e)&&(I.debounceRendering||E)(i)}function i(){var e,t=j;for(j=[];e=t.pop();)e.__d&&L(e)}function s(e,t,n){return"string"==typeof t||"number"==typeof t?void 0!==e.splitText:"string"==typeof t.nodeName?!e._componentConstructor&&a(e,t.nodeName):n||e._componentConstructor===t.nodeName}function a(e,t){return e.__n===t||e.nodeName.toLowerCase()===t.toLowerCase()}function l(e){var t=o({},e.attributes);t.children=e.children;var n=e.nodeName.defaultProps;if(void 0!==n)for(var r in n)void 0===t[r]&&(t[r]=n[r]);return t}function c(e,t){var n=t?document.createElementNS("http://www.w3.org/2000/svg",e):document.createElement(e);return n.__n=e,n}function u(e){var t=e.parentNode;t&&t.removeChild(e)}function h(e,t,n,o,r){if("className"===t&&(t="class"),"key"===t);else if("ref"===t)n&&n(null),o&&o(e);else if("class"!==t||r)if("style"===t){if(o&&"string"!=typeof o&&"string"!=typeof n||(e.style.cssText=o||""),o&&"object"==typeof o){if("string"!=typeof n)for(var i in n)i in o||(e.style[i]="");for(var i in o)e.style[i]="number"==typeof o[i]&&!1===T.test(i)?o[i]+"px":o[i]}}else if("dangerouslySetInnerHTML"===t)o&&(e.innerHTML=o.__html||"");else if("o"==t[0]&&"n"==t[1]){var s=t!==(t=t.replace(/Capture$/,""));t=t.toLowerCase().substring(2),o?n||e.addEventListener(t,p,s):e.removeEventListener(t,p,s),(e.__l||(e.__l={}))[t]=o}else if("list"!==t&&"type"!==t&&!r&&t in e)d(e,t,null==o?"":o),null!=o&&!1!==o||e.removeAttribute(t);else{var a=r&&t!==(t=t.replace(/^xlink\:?/,""));null==o||!1===o?a?e.removeAttributeNS("http://www.w3.org/1999/xlink",t.toLowerCase()):e.removeAttribute(t):"function"!=typeof o&&(a?e.setAttributeNS("http://www.w3.org/1999/xlink",t.toLowerCase(),o):e.setAttribute(t,o))}else e.className=o||""}function d(e,t,n){try{e[t]=n}catch(e){}}function p(e){return this.__l[e.type](I.event&&I.event(e)||e)}function f(){for(var e;e=P.pop();)I.afterMount&&I.afterMount(e),e.componentDidMount&&e.componentDidMount()}function v(e,t,n,o,r,i){R++||(U=null!=r&&void 0!==r.ownerSVGElement,D=null!=e&&!("__preactattr_"in e));var s=g(e,t,n,o,i);return r&&s.parentNode!==r&&r.appendChild(s),--R||(D=!1,i||f()),s}function g(e,t,n,o,r){var i=e,s=U;if(null!=t&&"boolean"!=typeof t||(t=""),"string"==typeof t||"number"==typeof t)return e&&void 0!==e.splitText&&e.parentNode&&(!e._component||r)?e.nodeValue!=t&&(e.nodeValue=t):(i=document.createTextNode(t),e&&(e.parentNode&&e.parentNode.replaceChild(i,e),y(e,!0))),i.__preactattr_=!0,i;var l=t.nodeName;if("function"==typeof l)return C(e,t,n,o);if(U="svg"===l||"foreignObject"!==l&&U,l=String(l),(!e||!a(e,l))&&(i=c(l,U),e)){for(;e.firstChild;)i.appendChild(e.firstChild);e.parentNode&&e.parentNode.replaceChild(i,e),y(e,!0)}var u=i.firstChild,h=i.__preactattr_,d=t.children;if(null==h){h=i.__preactattr_={};for(var p=i.attributes,f=p.length;f--;)h[p[f].name]=p[f].value}return!D&&d&&1===d.length&&"string"==typeof d[0]&&null!=u&&void 0!==u.splitText&&null==u.nextSibling?u.nodeValue!=d[0]&&(u.nodeValue=d[0]):(d&&d.length||null!=u)&&m(i,d,n,o,D||null!=h.dangerouslySetInnerHTML),k(i,t.attributes,h),U=s,i}function m(e,t,n,o,r){var i,a,l,c,h,d=e.childNodes,p=[],f={},v=0,m=0,_=d.length,k=0,b=t?t.length:0;if(0!==_)for(L=0;L<_;L++){var x=d[L],w=x.__preactattr_;null!=(S=b&&w?x._component?x._component.__k:w.key:null)?(v++,f[S]=x):(w||(void 0!==x.splitText?!r||x.nodeValue.trim():r))&&(p[k++]=x)}if(0!==b)for(L=0;L<b;L++){h=null;var S=(c=t[L]).key;if(null!=S)v&&void 0!==f[S]&&(h=f[S],f[S]=void 0,v--);else if(!h&&m<k)for(i=m;i<k;i++)if(void 0!==p[i]&&s(a=p[i],c,r)){h=a,p[i]=void 0,i===k-1&&k--,i===m&&m++;break}h=g(h,c,n,o),l=d[L],h&&h!==e&&h!==l&&(null==l?e.appendChild(h):h===l.nextSibling?u(l):e.insertBefore(h,l))}if(v)for(var L in f)void 0!==f[L]&&y(f[L],!1);for(;m<=k;)void 0!==(h=p[k--])&&y(h,!1)}function y(e,t){var n=e._component;n?M(n):(null!=e.__preactattr_&&e.__preactattr_.ref&&e.__preactattr_.ref(null),!1!==t&&null!=e.__preactattr_||u(e),_(e))}function _(e){for(e=e.lastChild;e;){var t=e.previousSibling;y(e,!0),e=t}}function k(e,t,n){var o;for(o in n)t&&null!=t[o]||null==n[o]||h(e,o,n[o],n[o]=void 0,U);for(o in t)"children"===o||"innerHTML"===o||o in n&&t[o]===("value"===o||"checked"===o?e[o]:n[o])||h(e,o,n[o],n[o]=t[o],U)}function b(e){var t=e.constructor.name;(V[t]||(V[t]=[])).push(e)}function x(e,t,n){var o,r=V[e.name];if(e.prototype&&e.prototype.render?(o=new e(t,n),N.call(o,t,n)):((o=new N(t,n)).constructor=e,o.render=w),r)for(var i=r.length;i--;)if(r[i].constructor===e){o.__b=r[i].__b,r.splice(i,1);break}return o}function w(e,t,n){return this.constructor(e,n)}function S(e,t,n,o,i){e.__x||(e.__x=!0,(e.__r=t.ref)&&delete t.ref,(e.__k=t.key)&&delete t.key,!e.base||i?e.componentWillMount&&e.componentWillMount():e.componentWillReceiveProps&&e.componentWillReceiveProps(t,o),o&&o!==e.context&&(e.__c||(e.__c=e.context),e.context=o),e.__p||(e.__p=e.props),e.props=t,e.__x=!1,0!==n&&(1!==n&&!1===I.syncComponentUpdates&&e.base?r(e):L(e,1,i)),e.__r&&e.__r(e))}function L(e,t,n,r){if(!e.__x){var i,s,a,c=e.props,u=e.state,h=e.context,d=e.__p||c,p=e.__s||u,g=e.__c||h,m=e.base,_=e.__b,k=m||_,b=e._component,w=!1;if(m&&(e.props=d,e.state=p,e.context=g,2!==t&&e.shouldComponentUpdate&&!1===e.shouldComponentUpdate(c,u,h)?w=!0:e.componentWillUpdate&&e.componentWillUpdate(c,u,h),e.props=c,e.state=u,e.context=h),e.__p=e.__s=e.__c=e.__b=null,e.__d=!1,!w){i=e.render(c,u,h),e.getChildContext&&(h=o(o({},h),e.getChildContext()));var C,N,A=i&&i.nodeName;if("function"==typeof A){var O=l(i);(s=b)&&s.constructor===A&&O.key==s.__k?S(s,O,1,h,!1):(C=s,e._component=s=x(A,O,h),s.__b=s.__b||_,s.__u=e,S(s,O,0,h,!1),L(s,1,n,!0)),N=s.base}else a=k,(C=b)&&(a=e._component=null),(k||1===t)&&(a&&(a._component=null),N=v(a,i,h,n||!m,k&&k.parentNode,!0));if(k&&N!==k&&s!==b){var E=k.parentNode;E&&N!==E&&(E.replaceChild(N,k),C||(k._component=null,y(k,!1)))}if(C&&M(C),e.base=N,N&&!r){for(var T=e,j=e;j=j.__u;)(T=j).base=N;N._component=T,N._componentConstructor=T.constructor}}if(!m||n?P.unshift(e):w||(e.componentDidUpdate&&e.componentDidUpdate(d,p,g),I.afterUpdate&&I.afterUpdate(e)),null!=e.__h)for(;e.__h.length;)e.__h.pop().call(e);R||r||f()}}function C(e,t,n,o){for(var r=e&&e._component,i=r,s=e,a=r&&e._componentConstructor===t.nodeName,c=a,u=l(t);r&&!c&&(r=r.__u);)c=r.constructor===t.nodeName;return r&&c&&(!o||r._component)?(S(r,u,3,n,o),e=r.base):(i&&!a&&(M(i),e=s=null),r=x(t.nodeName,u,n),e&&!r.__b&&(r.__b=e,s=null),S(r,u,1,n,o),e=r.base,s&&e!==s&&(s._component=null,y(s,!1))),e}function M(e){I.beforeUnmount&&I.beforeUnmount(e);var t=e.base;e.__x=!0,e.componentWillUnmount&&e.componentWillUnmount(),e.base=null;var n=e._component;n?M(n):t&&(t.__preactattr_&&t.__preactattr_.ref&&t.__preactattr_.ref(null),e.__b=t,u(t),b(e),_(t)),e.__r&&e.__r(null)}function N(e,t){this.__d=!0,this.context=t,this.props=e,this.state=this.state||{}}var I={},A=[],O=[],E="function"==typeof Promise?Promise.resolve().then.bind(Promise.resolve()):setTimeout,T=/acit|ex(?:s|g|n|p|$)|rph|ows|mnc|ntw|ine[ch]|zoo|^ord/i,j=[],P=[],R=0,U=!1,D=!1,V={};o(N.prototype,{setState:function(e,t){var n=this.state;this.__s||(this.__s=o({},n)),o(n,"function"==typeof e?e(n,this.props):e),t&&(this.__h=this.__h||[]).push(t),r(this)},forceUpdate:function(e){e&&(this.__h=this.__h||[]).push(e),L(this,2)},render:function(){}});var F={h:n,createElement:n,cloneElement:function(e,t){return n(e.nodeName,o(o({},e.attributes),t),arguments.length>2?[].slice.call(arguments,2):e.children)},Component:N,render:function(e,t,n){return v(n,e,{},!1,t,!1)},rerender:i,options:I};void 0!==t?t.exports=F:self.preact=F}()},{}]},{},[3]); +!function e(t,n,o){function r(s,a){if(!n[s]){if(!t[s]){var l="function"==typeof require&&require;if(!a&&l)return l(s,!0);if(i)return i(s,!0);var c=new Error("Cannot find module '"+s+"'");throw c.code="MODULE_NOT_FOUND",c}var u=n[s]={exports:{}};t[s][0].call(u.exports,function(e){var n=t[s][1][e];return r(n||e)},u,u.exports,e,t,n,o)}return n[s].exports}for(var i="function"==typeof require&&require,s=0;s<o.length;s++)r(o[s]);return r}({1:[function(e,t,n){"use strict";Object.defineProperty(n,"__esModule",{value:!0}),n.setCookie=function(e,t){document.cookie=e+"="+encodeURIComponent(t)+";path=/;"},n.clearCookie=function(e){document.cookie=e+"=;path=/;expires=Thu, 01-Jan-1970 00:00:01 GMT;"},n.getCookie=function(e){for(var t=e+"=",n=document.cookie.split(";"),o=0;o<n.length;o++){for(var r=n[o];" "==r.charAt(0);)r=r.substring(1,r.length);if(0==r.indexOf(t))return decodeURIComponent(r.substring(t.length,r.length))}return null}},{}],2:[function(e,t,n){"use strict";function o(e){var t=d[e];if(void 0==t)throw new Error("could not find <details> element with id '"+e+"'");return t}function r(e){for(var t=e.target,n=t.id,r=o(n),i=r.element.open,s=0,l=r.toggles;s<l.length;s++){var c=l[s];c.classList.contains("details-toggle-control")&&(c.classList.add(i?"collapser":"expander"),c.classList.remove(i?"expander":"collapser"))}t.open==r.openByDefault?delete p[n]:p[n]=!0,a()}function i(){for(var e=0,t=Array.prototype.slice.call(document.getElementsByTagName("details"));e<t.length;e++){var n=t[e];"string"==typeof n.id&&n.id.length>0&&(d[n.id]={element:n,openByDefault:!!n.open,toggles:[]},n.addEventListener("toggle",r))}}function s(e){var t=o(e).element;t.open=!t.open}function a(){var e=Object.keys(p);document.cookie="toggled="+encodeURIComponent(e.join("+"))}function l(){var e=h.getCookie("toggled");if(e)for(var t=0,n=e.split("+");t<n.length;t++){var o=n[t],r=d[o];p[o]=!0,r&&(r.element.open=!r.element.open)}}function c(e){e.preventDefault();var t=e.currentTarget.getAttribute("data-details-id");if(!t)throw new Error("element with class 'details-toggle' has no 'data-details-id' attribute!");s(t)}function u(){Array.prototype.slice.call(document.getElementsByClassName("details-toggle")).forEach(function(e){var t=e.getAttribute("data-details-id");if(!t)throw new Error("element with class 'details-toggle' has no 'data-details-id' attribute!");var n=o(t);n.toggles.push(e),e.addEventListener("click",c),e.classList.contains("details-toggle-control")&&e.classList.add(n.element.open?"collapser":"expander")})}Object.defineProperty(n,"__esModule",{value:!0});var h=e("./cookies"),d={},p={};n.init=function(){i(),l(),u()}},{"./cookies":1}],3:[function(e,t,n){"use strict";Object.defineProperty(n,"__esModule",{value:!0});var o=e("./style-menu"),r=e("./details-helper"),i=e("./quick-jump");!function(e){"interactive"===document.readyState?e():document.addEventListener("readystatechange",function(){"interactive"===document.readyState&&e()})}(function(){document.body.classList.add("js-enabled"),o.init(),r.init(),i.init()})},{"./details-helper":2,"./quick-jump":4,"./style-menu":5}],4:[function(e,t,n){"use strict";function o(e,t,n){var o=new XMLHttpRequest;o.onreadystatechange=function(){if(o.readyState===XMLHttpRequest.DONE)if(200===o.status){if(t)try{t(JSON.parse(o.responseText))}catch(e){n(o)}}else n&&n(o)},o.open("GET",e,!0),o.send()}function r(e){var t=document.querySelector("#page-menu"),n=document.createElement("li");t.insertBefore(n,t.firstChild),d.render(p(v,{onClick:e,title:"Quick Jump"}),t,n)}function i(e,t){return t.length<=e?t:t.slice(0,e)}function s(){return p("table",{class:"keyboard-shortcuts"},p("tr",null,p("th",null,"Key"),p("th",null,"Shortcut")),p("tr",null,p("td",null,p("span",{class:"key"},"s")),p("td",null,"Open this search box")),p("tr",null,p("td",null,p("span",{class:"key"},"esc")),p("td",null,"Close this search box")),p("tr",null,p("td",null,p("span",{class:"key"},"↓"),",",p("span",{class:"key"},"ctrl")," + ",p("span",{class:"key"},"j")),p("td",null,"Move down in search results")),p("tr",null,p("td",null,p("span",{class:"key"},"↑"),",",p("span",{class:"key"},"ctrl")," + ",p("span",{class:"key"},"k")),p("td",null,"Move up in search results")),p("tr",null,p("td",null,p("span",{class:"key"},"↵")),p("td",null,"Go to active search result")))}function a(){return p("p",null,"You can find any exported type, constructor, class, function or pattern defined in this package by (approximate) name.")}function l(e){var t=[p("p",null,"Your search for '",e.searchString,"' produced the following list of results: ",p("code",null,"[]"),"."),p("p",null,p("code",null,"Nothing")," matches your query for '",e.searchString,"'."),p("p",null,p("code",null,"Left \"no matches for '",e.searchString,"'\" :: Either String (NonEmpty SearchResult)"))];return t[(e.searchString||"a").charCodeAt(0)%t.length]}function c(e,t){d.render(p(g,{baseUrl:e||".",showHideTrigger:t||r}),document.body)}var u=this&&this.__extends||function(){var e=Object.setPrototypeOf||{__proto__:[]}instanceof Array&&function(e,t){e.__proto__=t}||function(e,t){for(var n in t)t.hasOwnProperty(n)&&(e[n]=t[n])};return function(t,n){function o(){this.constructor=t}e(t,n),t.prototype=null===n?Object.create(n):(o.prototype=n.prototype,new o)}}();Object.defineProperty(n,"__esModule",{value:!0});var h=e("fuse.js"),d=e("preact"),p=d.h,f=d.Component,v=function(e){function t(){return null!==e&&e.apply(this,arguments)||this}return u(t,e),t.prototype.render=function(e){return p("li",null,p("a",{href:"#",onClick:function(t){t.preventDefault(),e.onClick()}},e.title))},t}(f),g=function(e){function t(){var t=null!==e&&e.apply(this,arguments)||this;return t.linkIndex=0,t.focusPlease=!1,t.navigatedByKeyboard=!1,t}return u(t,e),t.prototype.componentWillMount=function(){var e=this;this.setState({searchString:"",isVisible:!1,expanded:{},activeLinkIndex:-1,moduleResults:[]}),o(this.props.baseUrl+"/doc-index.json",function(t){e.setState({fuse:new h(t,{threshold:.25,caseSensitive:!0,includeScore:!0,tokenize:!0,keys:[{name:"name",weight:.7},{name:"module",weight:.3}]}),moduleResults:[]})},function(t){console&&console.error("could not load 'doc-index.json' for searching",t),e.setState({failedLoading:!0})}),document.addEventListener("mousedown",this.hide.bind(this)),document.addEventListener("keydown",function(t){e.state.isVisible&&("Escape"===t.key?e.hide():"ArrowUp"===t.key||"k"===t.key&&t.ctrlKey?(t.preventDefault(),e.navigateLinks(-1)):"ArrowDown"===t.key||"j"===t.key&&t.ctrlKey?(t.preventDefault(),e.navigateLinks(1)):"Enter"===t.key&&e.state.activeLinkIndex>=0&&e.followActiveLink()),"s"===t.key&&"input"!==t.target.tagName.toLowerCase()&&(t.preventDefault(),e.show())})},t.prototype.hide=function(){this.setState({isVisible:!1,searchString:""})},t.prototype.show=function(){this.state.isVisible||(this.focusPlease=!0,this.setState({isVisible:!0,activeLinkIndex:-1}))},t.prototype.toggleVisibility=function(){this.state.isVisible?this.hide():this.show()},t.prototype.navigateLinks=function(e){var t=Math.max(-1,Math.min(this.linkIndex-1,this.state.activeLinkIndex+e));this.navigatedByKeyboard=!0,this.setState({activeLinkIndex:t})},t.prototype.followActiveLink=function(){this.activeLinkAction&&this.activeLinkAction()},t.prototype.updateResults=function(){var e=this.input&&this.input.value||"",t={};this.state.fuse.search(e).forEach(function(e){var n=e.item.module;(t[n]||(t[n]=[])).push(e)});var n=[];for(var o in t)!function(e){var o=t[e],r=0;o.forEach(function(e){r+=1/e.score}),n.push({module:e,totalScore:1/r,items:o})}(o);n.sort(function(e,t){return e.totalScore-t.totalScore}),this.setState({searchString:e,isVisible:!0,moduleResults:n})},t.prototype.componentDidUpdate=function(){if(this.searchResults&&this.activeLink&&this.navigatedByKeyboard){var e=this.activeLink.getClientRects()[0],t=this.searchResults.getClientRects()[0].top;e.bottom>window.innerHeight?this.searchResults.scrollTop+=e.bottom-window.innerHeight+80:e.top<t&&(this.searchResults.scrollTop-=t-e.top+80)}this.focusPlease&&this.input&&this.input.focus(),this.navigatedByKeyboard=!1,this.focusPlease=!1},t.prototype.componentDidMount=function(){this.props.showHideTrigger(this.toggleVisibility.bind(this))},t.prototype.render=function(e,t){var n=this;if(t.failedLoading){var o="file:"==window.location.protocol;return p("div",{id:"search",class:t.isVisible?"":"hidden"},p("div",{id:"search-results"},p("p",{class:"error"},"Failed to load file 'doc-index.json' containing definitions in this package."),o?p("p",{class:"error"},"To use quick jump, load this page with HTTP (from a local static file web server) instead of using the ",p("code",null,"file://")," protocol. (For security reasons, it is not possible to fetch auxiliary files using JS in a HTML page opened with ",p("code",null,"file://"),".)"):[]))}this.linkIndex=0;var r=function(e){e.stopPropagation()},c=i(10,t.moduleResults).map(function(e){return n.renderResultsInModule(e)});return p("div",{id:"search",class:t.isVisible?"":"hidden"},p("div",{id:"search-form",onMouseDown:r},p("input",{placeholder:"Search in package by name",ref:function(e){n.input=e},onFocus:this.show.bind(this),onClick:this.show.bind(this),onInput:this.updateResults.bind(this)})),p("div",{id:"search-results",ref:function(e){n.searchResults=e},onMouseDown:r,onMouseOver:function(e){for(var t=e.target;t&&"function"==typeof t.getAttribute;){var o=t.getAttribute("data-link-index");if("string"==typeof o){var r=parseInt(o,10);n.setState({activeLinkIndex:r});break}t=t.parentNode}}},""===t.searchString?[p(a,null),p(s,null)]:0==c.length?p(l,{searchString:t.searchString}):p("ul",null,c)))},t.prototype.renderResultsInModule=function(e){var t=this,n=e.items,o=e.module,r=this.state.expanded[o]||n.length<=10,s=r?n:i(8,n),a=function(e){return p("li",{class:"search-result"},t.navigationLink(t.props.baseUrl+"/"+e.link,{},p(m,{html:e.display_html})))};return p("li",{class:"search-module"},p("h4",null,o),p("ul",null,s.map(function(e){return a(e.item)}),r?[]:p("li",{class:"more-results"},this.actionLink(function(){var e=Object.assign({},t.state.expanded);e[o]=!0,t.setState({expanded:e})},{},"show "+(n.length-s.length)+" more results from this module"))))},t.prototype.navigationLink=function(e,t){for(var n=this,o=[],r=2;r<arguments.length;r++)o[r-2]=arguments[r];var i=Object.assign({href:e,onClick:this.hide.bind(this)},t);return this.menuLink.apply(this,[i,function(){window.location.href=e,n.hide()}].concat(o))},t.prototype.actionLink=function(e,t){for(var n=[],o=2;o<arguments.length;o++)n[o-2]=arguments[o];var r=Object.assign({href:"#",onClick:function(t){t.preventDefault(),e()}},t);return this.menuLink.apply(this,[r,e].concat(n))},t.prototype.menuLink=function(e,t){for(var n=this,o=[],r=2;r<arguments.length;r++)o[r-2]=arguments[r];var i=this.linkIndex;i===this.state.activeLinkIndex&&(e.class=(e.class?e.class+" ":"")+"active-link",e.ref=function(e){e&&(n.activeLink=e)},this.activeLinkAction=t);var s=Object.assign({"data-link-index":i},e);return this.linkIndex+=1,p.apply(void 0,["a",s].concat(o))},t}(f),m=function(e){function t(){return null!==e&&e.apply(this,arguments)||this}return u(t,e),t.prototype.shouldComponentUpdate=function(e){return this.props.html!==e.html},t.prototype.render=function(e){return p("div",{dangerouslySetInnerHTML:{__html:e.html}})},t}(f);n.init=c,window.quickNav={init:c}},{"fuse.js":6,preact:7}],5:[function(e,t,n){"use strict";function o(e){return(" "+e+" ").replace(g," ")}function r(e){return e.replace(m,"")}function i(e,t){return o(e.className||"").indexOf(" "+t+" ")>=0}function s(e,t){var n=o(e.className||"");n.indexOf(" "+t+" ")<0&&(e.className=r(n+" "+t))}function a(e,t){var n=o(e.className||"");n=n.replace(" "+t+" "," "),e.className=r(n)}function l(e,t,n,o){return null==o&&(o=!i(e,t)),o?(a(e,n),s(e,t)):(a(e,t),s(e,n)),o}function c(e){var t=document.getElementById("page-menu");if(t&&t.firstChild){var n=t.firstChild.cloneNode(!1);n.innerHTML=e,t.appendChild(n)}}function u(){return Array.prototype.slice.call(document.getElementsByTagName("link")).filter(function(e){return-1!=e.rel.indexOf("style")&&e.title})}function h(){var e=u(),t="";e.forEach(function(e){t+="<li><a href='#' onclick=\"setActiveStyleSheet('"+e.title+"'); return false;\">"+e.title+"</a></li>"}),e.length>1&&c("<div id='style-menu-holder'><a href='#' onclick='styleMenu(); return false;'>Style ▾</a><ul id='style-menu' class='hide'>"+t+"</ul></div>")}function d(e){for(var t=u(),n=null,o=0;o<t.length;o++){var r=t[o];r.disabled=!0,r.title==e&&(n=r)}n?(n.disabled=!1,v.setCookie("haddock-style",e)):(t[0].disabled=!1,v.clearCookie("haddock-style")),f(!1)}function p(){var e=v.getCookie("haddock-style");e&&d(e)}function f(e){var t=document.getElementById("style-menu");t&&y(t,e)}Object.defineProperty(n,"__esModule",{value:!0});var v=e("./cookies"),g=/\s\s+/g,m=/^\s+|\s+$/g,y=function(e,t){return function(n,o){return l(n,e,t,o)}}("show","hide");n.init=function(){h(),p()}},{"./cookies":1}],6:[function(e,t,n){!function(e,o){"object"==typeof n&&"object"==typeof t?t.exports=o():"function"==typeof define&&define.amd?define("Fuse",[],o):"object"==typeof n?n.Fuse=o():e.Fuse=o()}(this,function(){return function(e){function t(o){if(n[o])return n[o].exports;var r=n[o]={i:o,l:!1,exports:{}};return e[o].call(r.exports,r,r.exports,t),r.l=!0,r.exports}var n={};return t.m=e,t.c=n,t.i=function(e){return e},t.d=function(e,n,o){t.o(e,n)||Object.defineProperty(e,n,{configurable:!1,enumerable:!0,get:o})},t.n=function(e){var n=e&&e.__esModule?function(){return e.default}:function(){return e};return t.d(n,"a",n),n},t.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},t.p="",t(t.s=8)}([function(e,t,n){"use strict";e.exports=function(e){return"[object Array]"===Object.prototype.toString.call(e)}},function(e,t,n){"use strict";function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}var r=function(){function e(e,t){for(var n=0;n<t.length;n++){var o=t[n];o.enumerable=o.enumerable||!1,o.configurable=!0,"value"in o&&(o.writable=!0),Object.defineProperty(e,o.key,o)}}return function(t,n,o){return n&&e(t.prototype,n),o&&e(t,o),t}}(),i=n(5),s=n(7),a=n(4),l=function(){function e(t,n){var r=n.location,i=void 0===r?0:r,s=n.distance,l=void 0===s?100:s,c=n.threshold,u=void 0===c?.6:c,h=n.maxPatternLength,d=void 0===h?32:h,p=n.isCaseSensitive,f=void 0!==p&&p,v=n.tokenSeparator,g=void 0===v?/ +/g:v,m=n.findAllMatches,y=void 0!==m&&m,_=n.minMatchCharLength,k=void 0===_?1:_;o(this,e),this.options={location:i,distance:l,threshold:u,maxPatternLength:d,isCaseSensitive:f,tokenSeparator:g,findAllMatches:y,minMatchCharLength:k},this.pattern=this.options.isCaseSensitive?t:t.toLowerCase(),this.pattern.length<=d&&(this.patternAlphabet=a(this.pattern))}return r(e,[{key:"search",value:function(e){if(this.options.isCaseSensitive||(e=e.toLowerCase()),this.pattern===e)return{isMatch:!0,score:0,matchedIndices:[[0,e.length-1]]};var t=this.options,n=t.maxPatternLength,o=t.tokenSeparator;if(this.pattern.length>n)return i(e,this.pattern,o);var r=this.options,a=r.location,l=r.distance,c=r.threshold,u=r.findAllMatches,h=r.minMatchCharLength;return s(e,this.pattern,this.patternAlphabet,{location:a,distance:l,threshold:c,findAllMatches:u,minMatchCharLength:h})}}]),e}();e.exports=l},function(e,t,n){"use strict";var o=n(0),r=function e(t,n,r){if(n){var i=n.indexOf("."),s=n,a=null;-1!==i&&(s=n.slice(0,i),a=n.slice(i+1));var l=t[s];if(null!==l&&void 0!==l)if(a||"string"!=typeof l&&"number"!=typeof l)if(o(l))for(var c=0,u=l.length;c<u;c+=1)e(l[c],a,r);else a&&e(l,a,r);else r.push(l.toString())}else r.push(t);return r};e.exports=function(e,t){return r(e,t,[])}},function(e,t,n){"use strict";e.exports=function(){for(var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:[],t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:1,n=[],o=-1,r=-1,i=0,s=e.length;i<s;i+=1){var a=e[i];a&&-1===o?o=i:a||-1===o||((r=i-1)-o+1>=t&&n.push([o,r]),o=-1)}return e[i-1]&&i-o>=t&&n.push([o,i-1]),n}},function(e,t,n){"use strict";e.exports=function(e){for(var t={},n=e.length,o=0;o<n;o+=1)t[e.charAt(o)]=0;for(var r=0;r<n;r+=1)t[e.charAt(r)]|=1<<n-r-1;return t}},function(e,t,n){"use strict";var o=/[\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|]/g;e.exports=function(e,t){var n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:/ +/g,r=new RegExp(t.replace(o,"\\$&").replace(n,"|")),i=e.match(r),s=!!i,a=[];if(s)for(var l=0,c=i.length;l<c;l+=1){var u=i[l];a.push([e.indexOf(u),u.length-1])}return{score:s?.5:1,isMatch:s,matchedIndices:a}}},function(e,t,n){"use strict";e.exports=function(e,t){var n=t.errors,o=void 0===n?0:n,r=t.currentLocation,i=void 0===r?0:r,s=t.expectedLocation,a=void 0===s?0:s,l=t.distance,c=void 0===l?100:l,u=o/e.length,h=Math.abs(a-i);return c?u+h/c:h?1:u}},function(e,t,n){"use strict";var o=n(6),r=n(3);e.exports=function(e,t,n,i){for(var s=i.location,a=void 0===s?0:s,l=i.distance,c=void 0===l?100:l,u=i.threshold,h=void 0===u?.6:u,d=i.findAllMatches,p=void 0!==d&&d,f=i.minMatchCharLength,v=void 0===f?1:f,g=a,m=e.length,y=h,_=e.indexOf(t,g),k=t.length,b=[],x=0;x<m;x+=1)b[x]=0;if(-1!==_){var w=o(t,{errors:0,currentLocation:_,expectedLocation:g,distance:c});if(y=Math.min(w,y),-1!==(_=e.lastIndexOf(t,g+k))){var S=o(t,{errors:0,currentLocation:_,expectedLocation:g,distance:c});y=Math.min(S,y)}}_=-1;for(var L=[],C=1,M=k+m,N=1<<k-1,I=0;I<k;I+=1){for(var A=0,O=M;A<O;)o(t,{errors:I,currentLocation:g+O,expectedLocation:g,distance:c})<=y?A=O:M=O,O=Math.floor((M-A)/2+A);M=O;var E=Math.max(1,g-O+1),T=p?m:Math.min(g+O,m)+k,j=Array(T+2);j[T+1]=(1<<I)-1;for(var P=T;P>=E;P-=1){var R=P-1,U=n[e.charAt(R)];if(U&&(b[R]=1),j[P]=(j[P+1]<<1|1)&U,0!==I&&(j[P]|=(L[P+1]|L[P])<<1|1|L[P+1]),j[P]&N&&(C=o(t,{errors:I,currentLocation:R,expectedLocation:g,distance:c}))<=y){if(y=C,(_=R)<=g)break;E=Math.max(1,2*g-_)}}if(o(t,{errors:I+1,currentLocation:g,expectedLocation:g,distance:c})>y)break;L=j}return{isMatch:_>=0,score:0===C?.001:C,matchedIndices:r(b,v)}}},function(e,t,n){"use strict";function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}var r=function(){function e(e,t){for(var n=0;n<t.length;n++){var o=t[n];o.enumerable=o.enumerable||!1,o.configurable=!0,"value"in o&&(o.writable=!0),Object.defineProperty(e,o.key,o)}}return function(t,n,o){return n&&e(t.prototype,n),o&&e(t,o),t}}(),i=n(1),s=n(2),a=n(0),l=function(){function e(t,n){var r=n.location,i=void 0===r?0:r,a=n.distance,l=void 0===a?100:a,c=n.threshold,u=void 0===c?.6:c,h=n.maxPatternLength,d=void 0===h?32:h,p=n.caseSensitive,f=void 0!==p&&p,v=n.tokenSeparator,g=void 0===v?/ +/g:v,m=n.findAllMatches,y=void 0!==m&&m,_=n.minMatchCharLength,k=void 0===_?1:_,b=n.id,x=void 0===b?null:b,w=n.keys,S=void 0===w?[]:w,L=n.shouldSort,C=void 0===L||L,M=n.getFn,N=void 0===M?s:M,I=n.sortFn,A=void 0===I?function(e,t){return e.score-t.score}:I,O=n.tokenize,E=void 0!==O&&O,T=n.matchAllTokens,j=void 0!==T&&T,P=n.includeMatches,R=void 0!==P&&P,U=n.includeScore,D=void 0!==U&&U,V=n.verbose,F=void 0!==V&&V;o(this,e),this.options={location:i,distance:l,threshold:u,maxPatternLength:d,isCaseSensitive:f,tokenSeparator:g,findAllMatches:y,minMatchCharLength:k,id:x,keys:S,includeMatches:R,includeScore:D,shouldSort:C,getFn:N,sortFn:A,verbose:F,tokenize:E,matchAllTokens:j},this.setCollection(t)}return r(e,[{key:"setCollection",value:function(e){return this.list=e,e}},{key:"search",value:function(e){this._log('---------\nSearch pattern: "'+e+'"');var t=this._prepareSearchers(e),n=t.tokenSearchers,o=t.fullSearcher,r=this._search(n,o),i=r.weights,s=r.results;return this._computeScore(i,s),this.options.shouldSort&&this._sort(s),this._format(s)}},{key:"_prepareSearchers",value:function(){var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:"",t=[];if(this.options.tokenize)for(var n=e.split(this.options.tokenSeparator),o=0,r=n.length;o<r;o+=1)t.push(new i(n[o],this.options));return{tokenSearchers:t,fullSearcher:new i(e,this.options)}}},{key:"_search",value:function(){var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:[],t=arguments[1],n=this.list,o={},r=[];if("string"==typeof n[0]){for(var i=0,s=n.length;i<s;i+=1)this._analyze({key:"",value:n[i],record:i,index:i},{resultMap:o,results:r,tokenSearchers:e,fullSearcher:t});return{weights:null,results:r}}for(var a={},l=0,c=n.length;l<c;l+=1)for(var u=n[l],h=0,d=this.options.keys.length;h<d;h+=1){var p=this.options.keys[h];if("string"!=typeof p){if(a[p.name]={weight:1-p.weight||1},p.weight<=0||p.weight>1)throw new Error("Key weight has to be > 0 and <= 1");p=p.name}else a[p]={weight:1};this._analyze({key:p,value:this.options.getFn(u,p),record:u,index:l},{resultMap:o,results:r,tokenSearchers:e,fullSearcher:t})}return{weights:a,results:r}}},{key:"_analyze",value:function(e,t){var n=e.key,o=e.arrayIndex,r=void 0===o?-1:o,i=e.value,s=e.record,l=e.index,c=t.tokenSearchers,u=void 0===c?[]:c,h=t.fullSearcher,d=void 0===h?[]:h,p=t.resultMap,f=void 0===p?{}:p,v=t.results,g=void 0===v?[]:v;if(void 0!==i&&null!==i){var m=!1,y=-1,_=0;if("string"==typeof i){this._log("\nKey: "+(""===n?"-":n));var k=d.search(i);if(this._log('Full text: "'+i+'", score: '+k.score),this.options.tokenize){for(var b=i.split(this.options.tokenSeparator),x=[],w=0;w<u.length;w+=1){var S=u[w];this._log('\nPattern: "'+S.pattern+'"');for(var L=!1,C=0;C<b.length;C+=1){var M=b[C],N=S.search(M),I={};N.isMatch?(I[M]=N.score,m=!0,L=!0,x.push(N.score)):(I[M]=1,this.options.matchAllTokens||x.push(1)),this._log('Token: "'+M+'", score: '+I[M])}L&&(_+=1)}y=x[0];for(var A=x.length,O=1;O<A;O+=1)y+=x[O];y/=A,this._log("Token score average:",y)}var E=k.score;y>-1&&(E=(E+y)/2),this._log("Score average:",E);var T=!this.options.tokenize||!this.options.matchAllTokens||_>=u.length;if(this._log("\nCheck Matches: "+T),(m||k.isMatch)&&T){var j=f[l];j?j.output.push({key:n,arrayIndex:r,value:i,score:E,matchedIndices:k.matchedIndices}):(f[l]={item:s,output:[{key:n,arrayIndex:r,value:i,score:E,matchedIndices:k.matchedIndices}]},g.push(f[l]))}}else if(a(i))for(var P=0,R=i.length;P<R;P+=1)this._analyze({key:n,arrayIndex:P,value:i[P],record:s,index:l},{resultMap:f,results:g,tokenSearchers:u,fullSearcher:d})}}},{key:"_computeScore",value:function(e,t){this._log("\n\nComputing score:\n");for(var n=0,o=t.length;n<o;n+=1){for(var r=t[n].output,i=r.length,s=0,a=1,l=0;l<i;l+=1){var c=r[l].score,u=e?e[r[l].key].weight:1,h=c*u;1!==u?a=Math.min(a,h):(r[l].nScore=h,s+=h)}t[n].score=1===a?s/i:a,this._log(t[n])}}},{key:"_sort",value:function(e){this._log("\n\nSorting...."),e.sort(this.options.sortFn)}},{key:"_format",value:function(e){var t=[];this._log("\n\nOutput:\n\n",JSON.stringify(e));var n=[];this.options.includeMatches&&n.push(function(e,t){var n=e.output;t.matches=[];for(var o=0,r=n.length;o<r;o+=1){var i=n[o];if(0!==i.matchedIndices.length){var s={indices:i.matchedIndices,value:i.value};i.key&&(s.key=i.key),i.hasOwnProperty("arrayIndex")&&i.arrayIndex>-1&&(s.arrayIndex=i.arrayIndex),t.matches.push(s)}}}),this.options.includeScore&&n.push(function(e,t){t.score=e.score});for(var o=0,r=e.length;o<r;o+=1){var i=e[o];if(this.options.id&&(i.item=this.options.getFn(i.item,this.options.id)[0]),n.length){for(var s={item:i.item},a=0,l=n.length;a<l;a+=1)n[a](i,s);t.push(s)}else t.push(i.item)}return t}},{key:"_log",value:function(){if(this.options.verbose){var e;(e=console).log.apply(e,arguments)}}}]),e}();e.exports=l}])})},{}],7:[function(e,t,n){!function(){"use strict";function e(){}function n(t,n){var o,r,i,s,a=O;for(s=arguments.length;s-- >2;)A.push(arguments[s]);for(n&&null!=n.children&&(A.length||A.push(n.children),delete n.children);A.length;)if((r=A.pop())&&void 0!==r.pop)for(s=r.length;s--;)A.push(r[s]);else"boolean"==typeof r&&(r=null),(i="function"!=typeof t)&&(null==r?r="":"number"==typeof r?r=String(r):"string"!=typeof r&&(i=!1)),i&&o?a[a.length-1]+=r:a===O?a=[r]:a.push(r),o=i;var l=new e;return l.nodeName=t,l.children=a,l.attributes=null==n?void 0:n,l.key=null==n?void 0:n.key,void 0!==I.vnode&&I.vnode(l),l}function o(e,t){for(var n in t)e[n]=t[n];return e}function r(e){!e.__d&&(e.__d=!0)&&1==j.push(e)&&(I.debounceRendering||E)(i)}function i(){var e,t=j;for(j=[];e=t.pop();)e.__d&&L(e)}function s(e,t,n){return"string"==typeof t||"number"==typeof t?void 0!==e.splitText:"string"==typeof t.nodeName?!e._componentConstructor&&a(e,t.nodeName):n||e._componentConstructor===t.nodeName}function a(e,t){return e.__n===t||e.nodeName.toLowerCase()===t.toLowerCase()}function l(e){var t=o({},e.attributes);t.children=e.children;var n=e.nodeName.defaultProps;if(void 0!==n)for(var r in n)void 0===t[r]&&(t[r]=n[r]);return t}function c(e,t){var n=t?document.createElementNS("http://www.w3.org/2000/svg",e):document.createElement(e);return n.__n=e,n}function u(e){var t=e.parentNode;t&&t.removeChild(e)}function h(e,t,n,o,r){if("className"===t&&(t="class"),"key"===t);else if("ref"===t)n&&n(null),o&&o(e);else if("class"!==t||r)if("style"===t){if(o&&"string"!=typeof o&&"string"!=typeof n||(e.style.cssText=o||""),o&&"object"==typeof o){if("string"!=typeof n)for(var i in n)i in o||(e.style[i]="");for(var i in o)e.style[i]="number"==typeof o[i]&&!1===T.test(i)?o[i]+"px":o[i]}}else if("dangerouslySetInnerHTML"===t)o&&(e.innerHTML=o.__html||"");else if("o"==t[0]&&"n"==t[1]){var s=t!==(t=t.replace(/Capture$/,""));t=t.toLowerCase().substring(2),o?n||e.addEventListener(t,p,s):e.removeEventListener(t,p,s),(e.__l||(e.__l={}))[t]=o}else if("list"!==t&&"type"!==t&&!r&&t in e)d(e,t,null==o?"":o),null!=o&&!1!==o||e.removeAttribute(t);else{var a=r&&t!==(t=t.replace(/^xlink\:?/,""));null==o||!1===o?a?e.removeAttributeNS("http://www.w3.org/1999/xlink",t.toLowerCase()):e.removeAttribute(t):"function"!=typeof o&&(a?e.setAttributeNS("http://www.w3.org/1999/xlink",t.toLowerCase(),o):e.setAttribute(t,o))}else e.className=o||""}function d(e,t,n){try{e[t]=n}catch(e){}}function p(e){return this.__l[e.type](I.event&&I.event(e)||e)}function f(){for(var e;e=P.pop();)I.afterMount&&I.afterMount(e),e.componentDidMount&&e.componentDidMount()}function v(e,t,n,o,r,i){R++||(U=null!=r&&void 0!==r.ownerSVGElement,D=null!=e&&!("__preactattr_"in e));var s=g(e,t,n,o,i);return r&&s.parentNode!==r&&r.appendChild(s),--R||(D=!1,i||f()),s}function g(e,t,n,o,r){var i=e,s=U;if(null!=t&&"boolean"!=typeof t||(t=""),"string"==typeof t||"number"==typeof t)return e&&void 0!==e.splitText&&e.parentNode&&(!e._component||r)?e.nodeValue!=t&&(e.nodeValue=t):(i=document.createTextNode(t),e&&(e.parentNode&&e.parentNode.replaceChild(i,e),y(e,!0))),i.__preactattr_=!0,i;var l=t.nodeName;if("function"==typeof l)return C(e,t,n,o);if(U="svg"===l||"foreignObject"!==l&&U,l=String(l),(!e||!a(e,l))&&(i=c(l,U),e)){for(;e.firstChild;)i.appendChild(e.firstChild);e.parentNode&&e.parentNode.replaceChild(i,e),y(e,!0)}var u=i.firstChild,h=i.__preactattr_,d=t.children;if(null==h){h=i.__preactattr_={};for(var p=i.attributes,f=p.length;f--;)h[p[f].name]=p[f].value}return!D&&d&&1===d.length&&"string"==typeof d[0]&&null!=u&&void 0!==u.splitText&&null==u.nextSibling?u.nodeValue!=d[0]&&(u.nodeValue=d[0]):(d&&d.length||null!=u)&&m(i,d,n,o,D||null!=h.dangerouslySetInnerHTML),k(i,t.attributes,h),U=s,i}function m(e,t,n,o,r){var i,a,l,c,h,d=e.childNodes,p=[],f={},v=0,m=0,_=d.length,k=0,b=t?t.length:0;if(0!==_)for(L=0;L<_;L++){var x=d[L],w=x.__preactattr_;null!=(S=b&&w?x._component?x._component.__k:w.key:null)?(v++,f[S]=x):(w||(void 0!==x.splitText?!r||x.nodeValue.trim():r))&&(p[k++]=x)}if(0!==b)for(L=0;L<b;L++){h=null;var S=(c=t[L]).key;if(null!=S)v&&void 0!==f[S]&&(h=f[S],f[S]=void 0,v--);else if(!h&&m<k)for(i=m;i<k;i++)if(void 0!==p[i]&&s(a=p[i],c,r)){h=a,p[i]=void 0,i===k-1&&k--,i===m&&m++;break}h=g(h,c,n,o),l=d[L],h&&h!==e&&h!==l&&(null==l?e.appendChild(h):h===l.nextSibling?u(l):e.insertBefore(h,l))}if(v)for(var L in f)void 0!==f[L]&&y(f[L],!1);for(;m<=k;)void 0!==(h=p[k--])&&y(h,!1)}function y(e,t){var n=e._component;n?M(n):(null!=e.__preactattr_&&e.__preactattr_.ref&&e.__preactattr_.ref(null),!1!==t&&null!=e.__preactattr_||u(e),_(e))}function _(e){for(e=e.lastChild;e;){var t=e.previousSibling;y(e,!0),e=t}}function k(e,t,n){var o;for(o in n)t&&null!=t[o]||null==n[o]||h(e,o,n[o],n[o]=void 0,U);for(o in t)"children"===o||"innerHTML"===o||o in n&&t[o]===("value"===o||"checked"===o?e[o]:n[o])||h(e,o,n[o],n[o]=t[o],U)}function b(e){var t=e.constructor.name;(V[t]||(V[t]=[])).push(e)}function x(e,t,n){var o,r=V[e.name];if(e.prototype&&e.prototype.render?(o=new e(t,n),N.call(o,t,n)):((o=new N(t,n)).constructor=e,o.render=w),r)for(var i=r.length;i--;)if(r[i].constructor===e){o.__b=r[i].__b,r.splice(i,1);break}return o}function w(e,t,n){return this.constructor(e,n)}function S(e,t,n,o,i){e.__x||(e.__x=!0,(e.__r=t.ref)&&delete t.ref,(e.__k=t.key)&&delete t.key,!e.base||i?e.componentWillMount&&e.componentWillMount():e.componentWillReceiveProps&&e.componentWillReceiveProps(t,o),o&&o!==e.context&&(e.__c||(e.__c=e.context),e.context=o),e.__p||(e.__p=e.props),e.props=t,e.__x=!1,0!==n&&(1!==n&&!1===I.syncComponentUpdates&&e.base?r(e):L(e,1,i)),e.__r&&e.__r(e))}function L(e,t,n,r){if(!e.__x){var i,s,a,c=e.props,u=e.state,h=e.context,d=e.__p||c,p=e.__s||u,g=e.__c||h,m=e.base,_=e.__b,k=m||_,b=e._component,w=!1;if(m&&(e.props=d,e.state=p,e.context=g,2!==t&&e.shouldComponentUpdate&&!1===e.shouldComponentUpdate(c,u,h)?w=!0:e.componentWillUpdate&&e.componentWillUpdate(c,u,h),e.props=c,e.state=u,e.context=h),e.__p=e.__s=e.__c=e.__b=null,e.__d=!1,!w){i=e.render(c,u,h),e.getChildContext&&(h=o(o({},h),e.getChildContext()));var C,N,A=i&&i.nodeName;if("function"==typeof A){var O=l(i);(s=b)&&s.constructor===A&&O.key==s.__k?S(s,O,1,h,!1):(C=s,e._component=s=x(A,O,h),s.__b=s.__b||_,s.__u=e,S(s,O,0,h,!1),L(s,1,n,!0)),N=s.base}else a=k,(C=b)&&(a=e._component=null),(k||1===t)&&(a&&(a._component=null),N=v(a,i,h,n||!m,k&&k.parentNode,!0));if(k&&N!==k&&s!==b){var E=k.parentNode;E&&N!==E&&(E.replaceChild(N,k),C||(k._component=null,y(k,!1)))}if(C&&M(C),e.base=N,N&&!r){for(var T=e,j=e;j=j.__u;)(T=j).base=N;N._component=T,N._componentConstructor=T.constructor}}if(!m||n?P.unshift(e):w||(e.componentDidUpdate&&e.componentDidUpdate(d,p,g),I.afterUpdate&&I.afterUpdate(e)),null!=e.__h)for(;e.__h.length;)e.__h.pop().call(e);R||r||f()}}function C(e,t,n,o){for(var r=e&&e._component,i=r,s=e,a=r&&e._componentConstructor===t.nodeName,c=a,u=l(t);r&&!c&&(r=r.__u);)c=r.constructor===t.nodeName;return r&&c&&(!o||r._component)?(S(r,u,3,n,o),e=r.base):(i&&!a&&(M(i),e=s=null),r=x(t.nodeName,u,n),e&&!r.__b&&(r.__b=e,s=null),S(r,u,1,n,o),e=r.base,s&&e!==s&&(s._component=null,y(s,!1))),e}function M(e){I.beforeUnmount&&I.beforeUnmount(e);var t=e.base;e.__x=!0,e.componentWillUnmount&&e.componentWillUnmount(),e.base=null;var n=e._component;n?M(n):t&&(t.__preactattr_&&t.__preactattr_.ref&&t.__preactattr_.ref(null),e.__b=t,u(t),b(e),_(t)),e.__r&&e.__r(null)}function N(e,t){this.__d=!0,this.context=t,this.props=e,this.state=this.state||{}}var I={},A=[],O=[],E="function"==typeof Promise?Promise.resolve().then.bind(Promise.resolve()):setTimeout,T=/acit|ex(?:s|g|n|p|$)|rph|ows|mnc|ntw|ine[ch]|zoo|^ord/i,j=[],P=[],R=0,U=!1,D=!1,V={};o(N.prototype,{setState:function(e,t){var n=this.state;this.__s||(this.__s=o({},n)),o(n,"function"==typeof e?e(n,this.props):e),t&&(this.__h=this.__h||[]).push(t),r(this)},forceUpdate:function(e){e&&(this.__h=this.__h||[]).push(e),L(this,2)},render:function(){}});var F={h:n,createElement:n,cloneElement:function(e,t){return n(e.nodeName,o(o({},e.attributes),t),arguments.length>2?[].slice.call(arguments,2):e.children)},Component:N,render:function(e,t,n){return v(n,e,{},!1,t,!1)},rerender:i,options:I};void 0!==t?t.exports=F:self.preact=F}()},{}]},{},[3]); //# sourceMappingURL=haddock-bundle.min.js.map diff --git a/haddock-api/resources/html/js-src/quick-jump.tsx b/haddock-api/resources/html/js-src/quick-jump.tsx index 97ac14af..e64dae0b 100644 --- a/haddock-api/resources/html/js-src/quick-jump.tsx +++ b/haddock-api/resources/html/js-src/quick-jump.tsx @@ -107,7 +107,15 @@ class QuickJump extends Component<QuickJumpProps, QuickJumpState> { caseSensitive: true, includeScore: true, tokenize: true, - keys: ["name", "module"] + keys: [ { + name: "name", + weight: 0.7 + }, + { + name: "module", + weight: 0.3 + } + ] }), moduleResults: [] }); @@ -143,7 +151,7 @@ class QuickJump extends Component<QuickJumpProps, QuickJumpState> { } hide() { - this.setState({ isVisible: false }); + this.setState({ isVisible: false, searchString: '' }); } show() { @@ -409,4 +417,4 @@ export function init(docBaseUrl?: string, showHide?: (action: () => void) => voi } // export to global object -(window as any).quickNav = { init: init };
\ No newline at end of file +(window as any).quickNav = { init: init }; diff --git a/haddock-api/resources/html/quick-jump.css b/haddock-api/resources/html/quick-jump.css index ede05042..468d8036 100644 --- a/haddock-api/resources/html/quick-jump.css +++ b/haddock-api/resources/html/quick-jump.css @@ -8,6 +8,7 @@ width: 44em; z-index: 1000; pointer-events: none; + overflow-y: auto; } #search.hidden { @@ -42,7 +43,6 @@ box-sizing: border-box; border: 0.05em solid #b2d5fb; background: #e8f3ff; - overflow-y: auto; } #search-form input + #search-results { @@ -161,4 +161,4 @@ margin: 0 0.1em; } -/* @end */
\ No newline at end of file +/* @end */ diff --git a/haddock-api/resources/html/quick-jump.min.js b/haddock-api/resources/html/quick-jump.min.js index f22f8f28..c03e0836 100644 --- a/haddock-api/resources/html/quick-jump.min.js +++ b/haddock-api/resources/html/quick-jump.min.js @@ -1,2 +1,2 @@ -!function e(t,n,o){function r(s,a){if(!n[s]){if(!t[s]){var l="function"==typeof require&&require;if(!a&&l)return l(s,!0);if(i)return i(s,!0);var c=new Error("Cannot find module '"+s+"'");throw c.code="MODULE_NOT_FOUND",c}var u=n[s]={exports:{}};t[s][0].call(u.exports,function(e){var n=t[s][1][e];return r(n||e)},u,u.exports,e,t,n,o)}return n[s].exports}for(var i="function"==typeof require&&require,s=0;s<o.length;s++)r(o[s]);return r}({1:[function(e,t,n){"use strict";function o(e,t,n){var o=new XMLHttpRequest;o.onreadystatechange=function(){if(o.readyState===XMLHttpRequest.DONE)if(200===o.status){if(t)try{t(JSON.parse(o.responseText))}catch(e){n(o)}}else n&&n(o)},o.open("GET",e,!0),o.send()}function r(e){var t=document.querySelector("#page-menu"),n=document.createElement("li");t.insertBefore(n,t.firstChild),p.render(d(v,{onClick:e,title:"Quick Jump"}),t,n)}function i(e,t){return t.length<=e?t:t.slice(0,e)}function s(){return d("table",{class:"keyboard-shortcuts"},d("tr",null,d("th",null,"Key"),d("th",null,"Shortcut")),d("tr",null,d("td",null,d("span",{class:"key"},"s")),d("td",null,"Open this search box")),d("tr",null,d("td",null,d("span",{class:"key"},"esc")),d("td",null,"Close this search box")),d("tr",null,d("td",null,d("span",{class:"key"},"↓"),",",d("span",{class:"key"},"ctrl")," + ",d("span",{class:"key"},"j")),d("td",null,"Move down in search results")),d("tr",null,d("td",null,d("span",{class:"key"},"↑"),",",d("span",{class:"key"},"ctrl")," + ",d("span",{class:"key"},"k")),d("td",null,"Move up in search results")),d("tr",null,d("td",null,d("span",{class:"key"},"↵")),d("td",null,"Go to active search result")))}function a(){return d("p",null,"You can find any exported type, constructor, class, function or pattern defined in this package by (approximate) name.")}function l(e){var t=[d("p",null,"Your search for '",e.searchString,"' produced the following list of results: ",d("code",null,"[]"),"."),d("p",null,d("code",null,"Nothing")," matches your query for '",e.searchString,"'."),d("p",null,d("code",null,"Left \"no matches for '",e.searchString,"'\" :: Either String (NonEmpty SearchResult)"))];return t[(e.searchString||"a").charCodeAt(0)%t.length]}function c(e,t){p.render(d(_,{baseUrl:e||".",showHideTrigger:t||r}),document.body)}var u=this&&this.__extends||function(){var e=Object.setPrototypeOf||{__proto__:[]}instanceof Array&&function(e,t){e.__proto__=t}||function(e,t){for(var n in t)t.hasOwnProperty(n)&&(e[n]=t[n])};return function(t,n){function o(){this.constructor=t}e(t,n),t.prototype=null===n?Object.create(n):(o.prototype=n.prototype,new o)}}();Object.defineProperty(n,"__esModule",{value:!0});var h=e("fuse.js"),p=e("preact"),d=p.h,f=p.Component,v=function(e){function t(){return null!==e&&e.apply(this,arguments)||this}return u(t,e),t.prototype.render=function(e){return d("li",null,d("a",{href:"#",onClick:function(t){t.preventDefault(),e.onClick()}},e.title))},t}(f),_=function(e){function t(){var t=null!==e&&e.apply(this,arguments)||this;return t.linkIndex=0,t.focusPlease=!1,t.navigatedByKeyboard=!1,t}return u(t,e),t.prototype.componentWillMount=function(){var e=this;this.setState({searchString:"",isVisible:!1,expanded:{},activeLinkIndex:-1,moduleResults:[]}),o(this.props.baseUrl+"/doc-index.json",function(t){e.setState({fuse:new h(t,{threshold:.25,caseSensitive:!0,includeScore:!0,tokenize:!0,keys:["name","module"]}),moduleResults:[]})},function(t){console&&console.error("could not load 'doc-index.json' for searching",t),e.setState({failedLoading:!0})}),document.addEventListener("mousedown",this.hide.bind(this)),document.addEventListener("keydown",function(t){e.state.isVisible&&("Escape"===t.key?e.hide():"ArrowUp"===t.key||"k"===t.key&&t.ctrlKey?(t.preventDefault(),e.navigateLinks(-1)):"ArrowDown"===t.key||"j"===t.key&&t.ctrlKey?(t.preventDefault(),e.navigateLinks(1)):"Enter"===t.key&&e.state.activeLinkIndex>=0&&e.followActiveLink()),"s"===t.key&&"input"!==t.target.tagName.toLowerCase()&&(t.preventDefault(),e.show())})},t.prototype.hide=function(){this.setState({isVisible:!1})},t.prototype.show=function(){this.state.isVisible||(this.focusPlease=!0,this.setState({isVisible:!0,activeLinkIndex:-1}))},t.prototype.toggleVisibility=function(){this.state.isVisible?this.hide():this.show()},t.prototype.navigateLinks=function(e){var t=Math.max(-1,Math.min(this.linkIndex-1,this.state.activeLinkIndex+e));this.navigatedByKeyboard=!0,this.setState({activeLinkIndex:t})},t.prototype.followActiveLink=function(){this.activeLinkAction&&this.activeLinkAction()},t.prototype.updateResults=function(){var e=this.input&&this.input.value||"",t={};this.state.fuse.search(e).forEach(function(e){var n=e.item.module;(t[n]||(t[n]=[])).push(e)});var n=[];for(var o in t)!function(e){var o=t[e],r=0;o.forEach(function(e){r+=1/e.score}),n.push({module:e,totalScore:1/r,items:o})}(o);n.sort(function(e,t){return e.totalScore-t.totalScore}),this.setState({searchString:e,isVisible:!0,moduleResults:n})},t.prototype.componentDidUpdate=function(){if(this.searchResults&&this.activeLink&&this.navigatedByKeyboard){var e=this.activeLink.getClientRects()[0],t=this.searchResults.getClientRects()[0].top;e.bottom>window.innerHeight?this.searchResults.scrollTop+=e.bottom-window.innerHeight+80:e.top<t&&(this.searchResults.scrollTop-=t-e.top+80)}this.focusPlease&&this.input&&this.input.focus(),this.navigatedByKeyboard=!1,this.focusPlease=!1},t.prototype.componentDidMount=function(){this.props.showHideTrigger(this.toggleVisibility.bind(this))},t.prototype.render=function(e,t){var n=this;if(t.failedLoading){var o="file:"==window.location.protocol;return d("div",{id:"search",class:t.isVisible?"":"hidden"},d("div",{id:"search-results"},d("p",{class:"error"},"Failed to load file 'doc-index.json' containing definitions in this package."),o?d("p",{class:"error"},"To use quick jump, load this page with HTTP (from a local static file web server) instead of using the ",d("code",null,"file://")," protocol. (For security reasons, it is not possible to fetch auxiliary files using JS in a HTML page opened with ",d("code",null,"file://"),".)"):[]))}this.linkIndex=0;var r=function(e){e.stopPropagation()},c=i(10,t.moduleResults).map(function(e){return n.renderResultsInModule(e)});return d("div",{id:"search",class:t.isVisible?"":"hidden"},d("div",{id:"search-form",onMouseDown:r},d("input",{placeholder:"Search in package by name",ref:function(e){n.input=e},onFocus:this.show.bind(this),onClick:this.show.bind(this),onInput:this.updateResults.bind(this)})),d("div",{id:"search-results",ref:function(e){n.searchResults=e},onMouseDown:r,onMouseOver:function(e){for(var t=e.target;t&&"function"==typeof t.getAttribute;){var o=t.getAttribute("data-link-index");if("string"==typeof o){var r=parseInt(o,10);n.setState({activeLinkIndex:r});break}t=t.parentNode}}},""===t.searchString?[d(a,null),d(s,null)]:0==c.length?d(l,{searchString:t.searchString}):d("ul",null,c)))},t.prototype.renderResultsInModule=function(e){var t=this,n=e.items,o=e.module,r=this.state.expanded[o]||n.length<=10,s=r?n:i(8,n),a=function(e){return d("li",{class:"search-result"},t.navigationLink(t.props.baseUrl+"/"+e.link,{},d(g,{html:e.display_html})))};return d("li",{class:"search-module"},d("h4",null,o),d("ul",null,s.map(function(e){return a(e.item)}),r?[]:d("li",{class:"more-results"},this.actionLink(function(){var e=Object.assign({},t.state.expanded);e[o]=!0,t.setState({expanded:e})},{},"show "+(n.length-s.length)+" more results from this module"))))},t.prototype.navigationLink=function(e,t){for(var n=this,o=[],r=2;r<arguments.length;r++)o[r-2]=arguments[r];var i=Object.assign({href:e,onClick:this.hide.bind(this)},t),s=function(){window.location.href=e,n.hide()};return this.menuLink.apply(this,[i,s].concat(o))},t.prototype.actionLink=function(e,t){for(var n=[],o=2;o<arguments.length;o++)n[o-2]=arguments[o];var r=Object.assign({href:"#",onClick:function(t){t.preventDefault(),e()}},t);return this.menuLink.apply(this,[r,e].concat(n))},t.prototype.menuLink=function(e,t){for(var n=this,o=[],r=2;r<arguments.length;r++)o[r-2]=arguments[r];var i=this.linkIndex;i===this.state.activeLinkIndex&&(e.class=(e.class?e.class+" ":"")+"active-link",e.ref=function(e){e&&(n.activeLink=e)},this.activeLinkAction=t);var s=Object.assign({"data-link-index":i},e);return this.linkIndex+=1,d.apply(void 0,["a",s].concat(o))},t}(f),g=function(e){function t(){return null!==e&&e.apply(this,arguments)||this}return u(t,e),t.prototype.shouldComponentUpdate=function(e){return this.props.html!==e.html},t.prototype.render=function(e){return d("div",{dangerouslySetInnerHTML:{__html:e.html}})},t}(f);n.init=c,window.quickNav={init:c}},{"fuse.js":2,preact:3}],2:[function(e,t,n){!function(e,o){"object"==typeof n&&"object"==typeof t?t.exports=o():"function"==typeof define&&define.amd?define("Fuse",[],o):"object"==typeof n?n.Fuse=o():e.Fuse=o()}(this,function(){return function(e){function t(o){if(n[o])return n[o].exports;var r=n[o]={i:o,l:!1,exports:{}};return e[o].call(r.exports,r,r.exports,t),r.l=!0,r.exports}var n={};return t.m=e,t.c=n,t.i=function(e){return e},t.d=function(e,n,o){t.o(e,n)||Object.defineProperty(e,n,{configurable:!1,enumerable:!0,get:o})},t.n=function(e){var n=e&&e.__esModule?function(){return e.default}:function(){return e};return t.d(n,"a",n),n},t.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},t.p="",t(t.s=8)}([function(e,t,n){"use strict";e.exports=function(e){return"[object Array]"===Object.prototype.toString.call(e)}},function(e,t,n){"use strict";function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}var r=function(){function e(e,t){for(var n=0;n<t.length;n++){var o=t[n];o.enumerable=o.enumerable||!1,o.configurable=!0,"value"in o&&(o.writable=!0),Object.defineProperty(e,o.key,o)}}return function(t,n,o){return n&&e(t.prototype,n),o&&e(t,o),t}}(),i=n(5),s=n(7),a=n(4),l=function(){function e(t,n){var r=n.location,i=void 0===r?0:r,s=n.distance,l=void 0===s?100:s,c=n.threshold,u=void 0===c?.6:c,h=n.maxPatternLength,p=void 0===h?32:h,d=n.isCaseSensitive,f=void 0!==d&&d,v=n.tokenSeparator,_=void 0===v?/ +/g:v,g=n.findAllMatches,m=void 0!==g&&g,y=n.minMatchCharLength,k=void 0===y?1:y;o(this,e),this.options={location:i,distance:l,threshold:u,maxPatternLength:p,isCaseSensitive:f,tokenSeparator:_,findAllMatches:m,minMatchCharLength:k},this.pattern=this.options.isCaseSensitive?t:t.toLowerCase(),this.pattern.length<=p&&(this.patternAlphabet=a(this.pattern))}return r(e,[{key:"search",value:function(e){if(this.options.isCaseSensitive||(e=e.toLowerCase()),this.pattern===e)return{isMatch:!0,score:0,matchedIndices:[[0,e.length-1]]};var t=this.options,n=t.maxPatternLength,o=t.tokenSeparator;if(this.pattern.length>n)return i(e,this.pattern,o);var r=this.options,a=r.location,l=r.distance,c=r.threshold,u=r.findAllMatches,h=r.minMatchCharLength;return s(e,this.pattern,this.patternAlphabet,{location:a,distance:l,threshold:c,findAllMatches:u,minMatchCharLength:h})}}]),e}();e.exports=l},function(e,t,n){"use strict";var o=n(0),r=function e(t,n,r){if(n){var i=n.indexOf("."),s=n,a=null;-1!==i&&(s=n.slice(0,i),a=n.slice(i+1));var l=t[s];if(null!==l&&void 0!==l)if(a||"string"!=typeof l&&"number"!=typeof l)if(o(l))for(var c=0,u=l.length;c<u;c+=1)e(l[c],a,r);else a&&e(l,a,r);else r.push(l.toString())}else r.push(t);return r};e.exports=function(e,t){return r(e,t,[])}},function(e,t,n){"use strict";e.exports=function(){for(var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:[],t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:1,n=[],o=-1,r=-1,i=0,s=e.length;i<s;i+=1){var a=e[i];a&&-1===o?o=i:a||-1===o||((r=i-1)-o+1>=t&&n.push([o,r]),o=-1)}return e[i-1]&&i-o>=t&&n.push([o,i-1]),n}},function(e,t,n){"use strict";e.exports=function(e){for(var t={},n=e.length,o=0;o<n;o+=1)t[e.charAt(o)]=0;for(var r=0;r<n;r+=1)t[e.charAt(r)]|=1<<n-r-1;return t}},function(e,t,n){"use strict";var o=/[\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|]/g;e.exports=function(e,t){var n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:/ +/g,r=new RegExp(t.replace(o,"\\$&").replace(n,"|")),i=e.match(r),s=!!i,a=[];if(s)for(var l=0,c=i.length;l<c;l+=1){var u=i[l];a.push([e.indexOf(u),u.length-1])}return{score:s?.5:1,isMatch:s,matchedIndices:a}}},function(e,t,n){"use strict";e.exports=function(e,t){var n=t.errors,o=void 0===n?0:n,r=t.currentLocation,i=void 0===r?0:r,s=t.expectedLocation,a=void 0===s?0:s,l=t.distance,c=void 0===l?100:l,u=o/e.length,h=Math.abs(a-i);return c?u+h/c:h?1:u}},function(e,t,n){"use strict";var o=n(6),r=n(3);e.exports=function(e,t,n,i){for(var s=i.location,a=void 0===s?0:s,l=i.distance,c=void 0===l?100:l,u=i.threshold,h=void 0===u?.6:u,p=i.findAllMatches,d=void 0!==p&&p,f=i.minMatchCharLength,v=void 0===f?1:f,_=a,g=e.length,m=h,y=e.indexOf(t,_),k=t.length,b=[],x=0;x<g;x+=1)b[x]=0;if(-1!==y){var w=o(t,{errors:0,currentLocation:y,expectedLocation:_,distance:c});if(m=Math.min(w,m),-1!==(y=e.lastIndexOf(t,_+k))){var S=o(t,{errors:0,currentLocation:y,expectedLocation:_,distance:c});m=Math.min(S,m)}}y=-1;for(var L=[],C=1,M=k+g,N=1<<k-1,I=0;I<k;I+=1){for(var A=0,T=M;A<T;)o(t,{errors:I,currentLocation:_+T,expectedLocation:_,distance:c})<=m?A=T:M=T,T=Math.floor((M-A)/2+A);M=T;var O=Math.max(1,_-T+1),j=d?g:Math.min(_+T,g)+k,P=Array(j+2);P[j+1]=(1<<I)-1;for(var E=j;E>=O;E-=1){var R=E-1,U=n[e.charAt(R)];if(U&&(b[R]=1),P[E]=(P[E+1]<<1|1)&U,0!==I&&(P[E]|=(L[E+1]|L[E])<<1|1|L[E+1]),P[E]&N&&(C=o(t,{errors:I,currentLocation:R,expectedLocation:_,distance:c}))<=m){if(m=C,(y=R)<=_)break;O=Math.max(1,2*_-y)}}if(o(t,{errors:I+1,currentLocation:_,expectedLocation:_,distance:c})>m)break;L=P}return{isMatch:y>=0,score:0===C?.001:C,matchedIndices:r(b,v)}}},function(e,t,n){"use strict";function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}var r=function(){function e(e,t){for(var n=0;n<t.length;n++){var o=t[n];o.enumerable=o.enumerable||!1,o.configurable=!0,"value"in o&&(o.writable=!0),Object.defineProperty(e,o.key,o)}}return function(t,n,o){return n&&e(t.prototype,n),o&&e(t,o),t}}(),i=n(1),s=n(2),a=n(0),l=function(){function e(t,n){var r=n.location,i=void 0===r?0:r,a=n.distance,l=void 0===a?100:a,c=n.threshold,u=void 0===c?.6:c,h=n.maxPatternLength,p=void 0===h?32:h,d=n.caseSensitive,f=void 0!==d&&d,v=n.tokenSeparator,_=void 0===v?/ +/g:v,g=n.findAllMatches,m=void 0!==g&&g,y=n.minMatchCharLength,k=void 0===y?1:y,b=n.id,x=void 0===b?null:b,w=n.keys,S=void 0===w?[]:w,L=n.shouldSort,C=void 0===L||L,M=n.getFn,N=void 0===M?s:M,I=n.sortFn,A=void 0===I?function(e,t){return e.score-t.score}:I,T=n.tokenize,O=void 0!==T&&T,j=n.matchAllTokens,P=void 0!==j&&j,E=n.includeMatches,R=void 0!==E&&E,U=n.includeScore,D=void 0!==U&&U,V=n.verbose,F=void 0!==V&&V;o(this,e),this.options={location:i,distance:l,threshold:u,maxPatternLength:p,isCaseSensitive:f,tokenSeparator:_,findAllMatches:m,minMatchCharLength:k,id:x,keys:S,includeMatches:R,includeScore:D,shouldSort:C,getFn:N,sortFn:A,verbose:F,tokenize:O,matchAllTokens:P},this.setCollection(t)}return r(e,[{key:"setCollection",value:function(e){return this.list=e,e}},{key:"search",value:function(e){this._log('---------\nSearch pattern: "'+e+'"');var t=this._prepareSearchers(e),n=t.tokenSearchers,o=t.fullSearcher,r=this._search(n,o),i=r.weights,s=r.results;return this._computeScore(i,s),this.options.shouldSort&&this._sort(s),this._format(s)}},{key:"_prepareSearchers",value:function(){var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:"",t=[];if(this.options.tokenize)for(var n=e.split(this.options.tokenSeparator),o=0,r=n.length;o<r;o+=1)t.push(new i(n[o],this.options));return{tokenSearchers:t,fullSearcher:new i(e,this.options)}}},{key:"_search",value:function(){var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:[],t=arguments[1],n=this.list,o={},r=[];if("string"==typeof n[0]){for(var i=0,s=n.length;i<s;i+=1)this._analyze({key:"",value:n[i],record:i,index:i},{resultMap:o,results:r,tokenSearchers:e,fullSearcher:t});return{weights:null,results:r}}for(var a={},l=0,c=n.length;l<c;l+=1)for(var u=n[l],h=0,p=this.options.keys.length;h<p;h+=1){var d=this.options.keys[h];if("string"!=typeof d){if(a[d.name]={weight:1-d.weight||1},d.weight<=0||d.weight>1)throw new Error("Key weight has to be > 0 and <= 1");d=d.name}else a[d]={weight:1};this._analyze({key:d,value:this.options.getFn(u,d),record:u,index:l},{resultMap:o,results:r,tokenSearchers:e,fullSearcher:t})}return{weights:a,results:r}}},{key:"_analyze",value:function(e,t){var n=e.key,o=e.arrayIndex,r=void 0===o?-1:o,i=e.value,s=e.record,l=e.index,c=t.tokenSearchers,u=void 0===c?[]:c,h=t.fullSearcher,p=void 0===h?[]:h,d=t.resultMap,f=void 0===d?{}:d,v=t.results,_=void 0===v?[]:v;if(void 0!==i&&null!==i){var g=!1,m=-1,y=0;if("string"==typeof i){this._log("\nKey: "+(""===n?"-":n));var k=p.search(i);if(this._log('Full text: "'+i+'", score: '+k.score),this.options.tokenize){for(var b=i.split(this.options.tokenSeparator),x=[],w=0;w<u.length;w+=1){var S=u[w];this._log('\nPattern: "'+S.pattern+'"');for(var L=!1,C=0;C<b.length;C+=1){var M=b[C],N=S.search(M),I={};N.isMatch?(I[M]=N.score,g=!0,L=!0,x.push(N.score)):(I[M]=1,this.options.matchAllTokens||x.push(1)),this._log('Token: "'+M+'", score: '+I[M])}L&&(y+=1)}m=x[0];for(var A=x.length,T=1;T<A;T+=1)m+=x[T];m/=A,this._log("Token score average:",m)}var O=k.score;m>-1&&(O=(O+m)/2),this._log("Score average:",O);var j=!this.options.tokenize||!this.options.matchAllTokens||y>=u.length;if(this._log("\nCheck Matches: "+j),(g||k.isMatch)&&j){var P=f[l];P?P.output.push({key:n,arrayIndex:r,value:i,score:O,matchedIndices:k.matchedIndices}):(f[l]={item:s,output:[{key:n,arrayIndex:r,value:i,score:O,matchedIndices:k.matchedIndices}]},_.push(f[l]))}}else if(a(i))for(var E=0,R=i.length;E<R;E+=1)this._analyze({key:n,arrayIndex:E,value:i[E],record:s,index:l},{resultMap:f,results:_,tokenSearchers:u,fullSearcher:p})}}},{key:"_computeScore",value:function(e,t){this._log("\n\nComputing score:\n");for(var n=0,o=t.length;n<o;n+=1){for(var r=t[n].output,i=r.length,s=0,a=1,l=0;l<i;l+=1){var c=e?e[r[l].key].weight:1,u=(1===c?r[l].score:r[l].score||.001)*c;1!==c?a=Math.min(a,u):(r[l].nScore=u,s+=u)}t[n].score=1===a?s/i:a,this._log(t[n])}}},{key:"_sort",value:function(e){this._log("\n\nSorting...."),e.sort(this.options.sortFn)}},{key:"_format",value:function(e){var t=[];this._log("\n\nOutput:\n\n",JSON.stringify(e));var n=[];this.options.includeMatches&&n.push(function(e,t){var n=e.output;t.matches=[];for(var o=0,r=n.length;o<r;o+=1){var i=n[o];if(0!==i.matchedIndices.length){var s={indices:i.matchedIndices,value:i.value};i.key&&(s.key=i.key),i.hasOwnProperty("arrayIndex")&&i.arrayIndex>-1&&(s.arrayIndex=i.arrayIndex),t.matches.push(s)}}}),this.options.includeScore&&n.push(function(e,t){t.score=e.score});for(var o=0,r=e.length;o<r;o+=1){var i=e[o];if(this.options.id&&(i.item=this.options.getFn(i.item,this.options.id)[0]),n.length){for(var s={item:i.item},a=0,l=n.length;a<l;a+=1)n[a](i,s);t.push(s)}else t.push(i.item)}return t}},{key:"_log",value:function(){if(this.options.verbose){var e;(e=console).log.apply(e,arguments)}}}]),e}();e.exports=l}])})},{}],3:[function(e,t,n){!function(){"use strict";function e(){}function n(t,n){var o,r,i,s,a=T;for(s=arguments.length;s-- >2;)A.push(arguments[s]);for(n&&null!=n.children&&(A.length||A.push(n.children),delete n.children);A.length;)if((r=A.pop())&&void 0!==r.pop)for(s=r.length;s--;)A.push(r[s]);else"boolean"==typeof r&&(r=null),(i="function"!=typeof t)&&(null==r?r="":"number"==typeof r?r=String(r):"string"!=typeof r&&(i=!1)),i&&o?a[a.length-1]+=r:a===T?a=[r]:a.push(r),o=i;var l=new e;return l.nodeName=t,l.children=a,l.attributes=null==n?void 0:n,l.key=null==n?void 0:n.key,void 0!==I.vnode&&I.vnode(l),l}function o(e,t){for(var n in t)e[n]=t[n];return e}function r(e){!e.__d&&(e.__d=!0)&&1==P.push(e)&&(I.debounceRendering||O)(i)}function i(){var e,t=P;for(P=[];e=t.pop();)e.__d&&L(e)}function s(e,t,n){return"string"==typeof t||"number"==typeof t?void 0!==e.splitText:"string"==typeof t.nodeName?!e._componentConstructor&&a(e,t.nodeName):n||e._componentConstructor===t.nodeName}function a(e,t){return e.__n===t||e.nodeName.toLowerCase()===t.toLowerCase()}function l(e){var t=o({},e.attributes);t.children=e.children;var n=e.nodeName.defaultProps;if(void 0!==n)for(var r in n)void 0===t[r]&&(t[r]=n[r]);return t}function c(e,t){var n=t?document.createElementNS("http://www.w3.org/2000/svg",e):document.createElement(e);return n.__n=e,n}function u(e){var t=e.parentNode;t&&t.removeChild(e)}function h(e,t,n,o,r){if("className"===t&&(t="class"),"key"===t);else if("ref"===t)n&&n(null),o&&o(e);else if("class"!==t||r)if("style"===t){if(o&&"string"!=typeof o&&"string"!=typeof n||(e.style.cssText=o||""),o&&"object"==typeof o){if("string"!=typeof n)for(var i in n)i in o||(e.style[i]="");for(var i in o)e.style[i]="number"==typeof o[i]&&!1===j.test(i)?o[i]+"px":o[i]}}else if("dangerouslySetInnerHTML"===t)o&&(e.innerHTML=o.__html||"");else if("o"==t[0]&&"n"==t[1]){var s=t!==(t=t.replace(/Capture$/,""));t=t.toLowerCase().substring(2),o?n||e.addEventListener(t,d,s):e.removeEventListener(t,d,s),(e.__l||(e.__l={}))[t]=o}else if("list"!==t&&"type"!==t&&!r&&t in e)p(e,t,null==o?"":o),null!=o&&!1!==o||e.removeAttribute(t);else{var a=r&&t!==(t=t.replace(/^xlink\:?/,""));null==o||!1===o?a?e.removeAttributeNS("http://www.w3.org/1999/xlink",t.toLowerCase()):e.removeAttribute(t):"function"!=typeof o&&(a?e.setAttributeNS("http://www.w3.org/1999/xlink",t.toLowerCase(),o):e.setAttribute(t,o))}else e.className=o||""}function p(e,t,n){try{e[t]=n}catch(e){}}function d(e){return this.__l[e.type](I.event&&I.event(e)||e)}function f(){for(var e;e=E.pop();)I.afterMount&&I.afterMount(e),e.componentDidMount&&e.componentDidMount()}function v(e,t,n,o,r,i){R++||(U=null!=r&&void 0!==r.ownerSVGElement,D=null!=e&&!("__preactattr_"in e));var s=_(e,t,n,o,i);return r&&s.parentNode!==r&&r.appendChild(s),--R||(D=!1,i||f()),s}function _(e,t,n,o,r){var i=e,s=U;if(null!=t&&"boolean"!=typeof t||(t=""),"string"==typeof t||"number"==typeof t)return e&&void 0!==e.splitText&&e.parentNode&&(!e._component||r)?e.nodeValue!=t&&(e.nodeValue=t):(i=document.createTextNode(t),e&&(e.parentNode&&e.parentNode.replaceChild(i,e),m(e,!0))),i.__preactattr_=!0,i;var l=t.nodeName;if("function"==typeof l)return C(e,t,n,o);if(U="svg"===l||"foreignObject"!==l&&U,l=String(l),(!e||!a(e,l))&&(i=c(l,U),e)){for(;e.firstChild;)i.appendChild(e.firstChild);e.parentNode&&e.parentNode.replaceChild(i,e),m(e,!0)}var u=i.firstChild,h=i.__preactattr_,p=t.children;if(null==h){h=i.__preactattr_={};for(var d=i.attributes,f=d.length;f--;)h[d[f].name]=d[f].value}return!D&&p&&1===p.length&&"string"==typeof p[0]&&null!=u&&void 0!==u.splitText&&null==u.nextSibling?u.nodeValue!=p[0]&&(u.nodeValue=p[0]):(p&&p.length||null!=u)&&g(i,p,n,o,D||null!=h.dangerouslySetInnerHTML),k(i,t.attributes,h),U=s,i}function g(e,t,n,o,r){var i,a,l,c,h,p=e.childNodes,d=[],f={},v=0,g=0,y=p.length,k=0,b=t?t.length:0;if(0!==y)for(L=0;L<y;L++){var x=p[L],w=x.__preactattr_;null!=(S=b&&w?x._component?x._component.__k:w.key:null)?(v++,f[S]=x):(w||(void 0!==x.splitText?!r||x.nodeValue.trim():r))&&(d[k++]=x)}if(0!==b)for(L=0;L<b;L++){h=null;var S=(c=t[L]).key;if(null!=S)v&&void 0!==f[S]&&(h=f[S],f[S]=void 0,v--);else if(!h&&g<k)for(i=g;i<k;i++)if(void 0!==d[i]&&s(a=d[i],c,r)){h=a,d[i]=void 0,i===k-1&&k--,i===g&&g++;break}h=_(h,c,n,o),l=p[L],h&&h!==e&&h!==l&&(null==l?e.appendChild(h):h===l.nextSibling?u(l):e.insertBefore(h,l))}if(v)for(var L in f)void 0!==f[L]&&m(f[L],!1);for(;g<=k;)void 0!==(h=d[k--])&&m(h,!1)}function m(e,t){var n=e._component;n?M(n):(null!=e.__preactattr_&&e.__preactattr_.ref&&e.__preactattr_.ref(null),!1!==t&&null!=e.__preactattr_||u(e),y(e))}function y(e){for(e=e.lastChild;e;){var t=e.previousSibling;m(e,!0),e=t}}function k(e,t,n){var o;for(o in n)t&&null!=t[o]||null==n[o]||h(e,o,n[o],n[o]=void 0,U);for(o in t)"children"===o||"innerHTML"===o||o in n&&t[o]===("value"===o||"checked"===o?e[o]:n[o])||h(e,o,n[o],n[o]=t[o],U)}function b(e){var t=e.constructor.name;(V[t]||(V[t]=[])).push(e)}function x(e,t,n){var o,r=V[e.name];if(e.prototype&&e.prototype.render?(o=new e(t,n),N.call(o,t,n)):((o=new N(t,n)).constructor=e,o.render=w),r)for(var i=r.length;i--;)if(r[i].constructor===e){o.__b=r[i].__b,r.splice(i,1);break}return o}function w(e,t,n){return this.constructor(e,n)}function S(e,t,n,o,i){e.__x||(e.__x=!0,(e.__r=t.ref)&&delete t.ref,(e.__k=t.key)&&delete t.key,!e.base||i?e.componentWillMount&&e.componentWillMount():e.componentWillReceiveProps&&e.componentWillReceiveProps(t,o),o&&o!==e.context&&(e.__c||(e.__c=e.context),e.context=o),e.__p||(e.__p=e.props),e.props=t,e.__x=!1,0!==n&&(1!==n&&!1===I.syncComponentUpdates&&e.base?r(e):L(e,1,i)),e.__r&&e.__r(e))}function L(e,t,n,r){if(!e.__x){var i,s,a,c=e.props,u=e.state,h=e.context,p=e.__p||c,d=e.__s||u,_=e.__c||h,g=e.base,y=e.__b,k=g||y,b=e._component,w=!1;if(g&&(e.props=p,e.state=d,e.context=_,2!==t&&e.shouldComponentUpdate&&!1===e.shouldComponentUpdate(c,u,h)?w=!0:e.componentWillUpdate&&e.componentWillUpdate(c,u,h),e.props=c,e.state=u,e.context=h),e.__p=e.__s=e.__c=e.__b=null,e.__d=!1,!w){i=e.render(c,u,h),e.getChildContext&&(h=o(o({},h),e.getChildContext()));var C,N,A=i&&i.nodeName;if("function"==typeof A){var T=l(i);(s=b)&&s.constructor===A&&T.key==s.__k?S(s,T,1,h,!1):(C=s,e._component=s=x(A,T,h),s.__b=s.__b||y,s.__u=e,S(s,T,0,h,!1),L(s,1,n,!0)),N=s.base}else a=k,(C=b)&&(a=e._component=null),(k||1===t)&&(a&&(a._component=null),N=v(a,i,h,n||!g,k&&k.parentNode,!0));if(k&&N!==k&&s!==b){var O=k.parentNode;O&&N!==O&&(O.replaceChild(N,k),C||(k._component=null,m(k,!1)))}if(C&&M(C),e.base=N,N&&!r){for(var j=e,P=e;P=P.__u;)(j=P).base=N;N._component=j,N._componentConstructor=j.constructor}}if(!g||n?E.unshift(e):w||(e.componentDidUpdate&&e.componentDidUpdate(p,d,_),I.afterUpdate&&I.afterUpdate(e)),null!=e.__h)for(;e.__h.length;)e.__h.pop().call(e);R||r||f()}}function C(e,t,n,o){for(var r=e&&e._component,i=r,s=e,a=r&&e._componentConstructor===t.nodeName,c=a,u=l(t);r&&!c&&(r=r.__u);)c=r.constructor===t.nodeName;return r&&c&&(!o||r._component)?(S(r,u,3,n,o),e=r.base):(i&&!a&&(M(i),e=s=null),r=x(t.nodeName,u,n),e&&!r.__b&&(r.__b=e,s=null),S(r,u,1,n,o),e=r.base,s&&e!==s&&(s._component=null,m(s,!1))),e}function M(e){I.beforeUnmount&&I.beforeUnmount(e);var t=e.base;e.__x=!0,e.componentWillUnmount&&e.componentWillUnmount(),e.base=null;var n=e._component;n?M(n):t&&(t.__preactattr_&&t.__preactattr_.ref&&t.__preactattr_.ref(null),e.__b=t,u(t),b(e),y(t)),e.__r&&e.__r(null)}function N(e,t){this.__d=!0,this.context=t,this.props=e,this.state=this.state||{}}var I={},A=[],T=[],O="function"==typeof Promise?Promise.resolve().then.bind(Promise.resolve()):setTimeout,j=/acit|ex(?:s|g|n|p|$)|rph|ows|mnc|ntw|ine[ch]|zoo|^ord/i,P=[],E=[],R=0,U=!1,D=!1,V={};o(N.prototype,{setState:function(e,t){var n=this.state;this.__s||(this.__s=o({},n)),o(n,"function"==typeof e?e(n,this.props):e),t&&(this.__h=this.__h||[]).push(t),r(this)},forceUpdate:function(e){e&&(this.__h=this.__h||[]).push(e),L(this,2)},render:function(){}});var F={h:n,createElement:n,cloneElement:function(e,t){return n(e.nodeName,o(o({},e.attributes),t),arguments.length>2?[].slice.call(arguments,2):e.children)},Component:N,render:function(e,t,n){return v(n,e,{},!1,t,!1)},rerender:i,options:I};void 0!==t?t.exports=F:self.preact=F}()},{}]},{},[1]); +!function e(t,n,o){function r(s,a){if(!n[s]){if(!t[s]){var l="function"==typeof require&&require;if(!a&&l)return l(s,!0);if(i)return i(s,!0);var c=new Error("Cannot find module '"+s+"'");throw c.code="MODULE_NOT_FOUND",c}var u=n[s]={exports:{}};t[s][0].call(u.exports,function(e){var n=t[s][1][e];return r(n||e)},u,u.exports,e,t,n,o)}return n[s].exports}for(var i="function"==typeof require&&require,s=0;s<o.length;s++)r(o[s]);return r}({1:[function(e,t,n){"use strict";function o(e,t,n){var o=new XMLHttpRequest;o.onreadystatechange=function(){if(o.readyState===XMLHttpRequest.DONE)if(200===o.status){if(t)try{t(JSON.parse(o.responseText))}catch(e){n(o)}}else n&&n(o)},o.open("GET",e,!0),o.send()}function r(e){var t=document.querySelector("#page-menu"),n=document.createElement("li");t.insertBefore(n,t.firstChild),p.render(d(v,{onClick:e,title:"Quick Jump"}),t,n)}function i(e,t){return t.length<=e?t:t.slice(0,e)}function s(){return d("table",{class:"keyboard-shortcuts"},d("tr",null,d("th",null,"Key"),d("th",null,"Shortcut")),d("tr",null,d("td",null,d("span",{class:"key"},"s")),d("td",null,"Open this search box")),d("tr",null,d("td",null,d("span",{class:"key"},"esc")),d("td",null,"Close this search box")),d("tr",null,d("td",null,d("span",{class:"key"},"↓"),",",d("span",{class:"key"},"ctrl")," + ",d("span",{class:"key"},"j")),d("td",null,"Move down in search results")),d("tr",null,d("td",null,d("span",{class:"key"},"↑"),",",d("span",{class:"key"},"ctrl")," + ",d("span",{class:"key"},"k")),d("td",null,"Move up in search results")),d("tr",null,d("td",null,d("span",{class:"key"},"↵")),d("td",null,"Go to active search result")))}function a(){return d("p",null,"You can find any exported type, constructor, class, function or pattern defined in this package by (approximate) name.")}function l(e){var t=[d("p",null,"Your search for '",e.searchString,"' produced the following list of results: ",d("code",null,"[]"),"."),d("p",null,d("code",null,"Nothing")," matches your query for '",e.searchString,"'."),d("p",null,d("code",null,"Left \"no matches for '",e.searchString,"'\" :: Either String (NonEmpty SearchResult)"))];return t[(e.searchString||"a").charCodeAt(0)%t.length]}function c(e,t){p.render(d(_,{baseUrl:e||".",showHideTrigger:t||r}),document.body)}var u=this&&this.__extends||function(){var e=Object.setPrototypeOf||{__proto__:[]}instanceof Array&&function(e,t){e.__proto__=t}||function(e,t){for(var n in t)t.hasOwnProperty(n)&&(e[n]=t[n])};return function(t,n){function o(){this.constructor=t}e(t,n),t.prototype=null===n?Object.create(n):(o.prototype=n.prototype,new o)}}();Object.defineProperty(n,"__esModule",{value:!0});var h=e("fuse.js"),p=e("preact"),d=p.h,f=p.Component,v=function(e){function t(){return null!==e&&e.apply(this,arguments)||this}return u(t,e),t.prototype.render=function(e){return d("li",null,d("a",{href:"#",onClick:function(t){t.preventDefault(),e.onClick()}},e.title))},t}(f),_=function(e){function t(){var t=null!==e&&e.apply(this,arguments)||this;return t.linkIndex=0,t.focusPlease=!1,t.navigatedByKeyboard=!1,t}return u(t,e),t.prototype.componentWillMount=function(){var e=this;this.setState({searchString:"",isVisible:!1,expanded:{},activeLinkIndex:-1,moduleResults:[]}),o(this.props.baseUrl+"/doc-index.json",function(t){e.setState({fuse:new h(t,{threshold:.25,caseSensitive:!0,includeScore:!0,tokenize:!0,keys:[{name:"name",weight:.7},{name:"module",weight:.3}]}),moduleResults:[]})},function(t){console&&console.error("could not load 'doc-index.json' for searching",t),e.setState({failedLoading:!0})}),document.addEventListener("mousedown",this.hide.bind(this)),document.addEventListener("keydown",function(t){e.state.isVisible&&("Escape"===t.key?e.hide():"ArrowUp"===t.key||"k"===t.key&&t.ctrlKey?(t.preventDefault(),e.navigateLinks(-1)):"ArrowDown"===t.key||"j"===t.key&&t.ctrlKey?(t.preventDefault(),e.navigateLinks(1)):"Enter"===t.key&&e.state.activeLinkIndex>=0&&e.followActiveLink()),"s"===t.key&&"input"!==t.target.tagName.toLowerCase()&&(t.preventDefault(),e.show())})},t.prototype.hide=function(){this.setState({isVisible:!1,searchString:""})},t.prototype.show=function(){this.state.isVisible||(this.focusPlease=!0,this.setState({isVisible:!0,activeLinkIndex:-1}))},t.prototype.toggleVisibility=function(){this.state.isVisible?this.hide():this.show()},t.prototype.navigateLinks=function(e){var t=Math.max(-1,Math.min(this.linkIndex-1,this.state.activeLinkIndex+e));this.navigatedByKeyboard=!0,this.setState({activeLinkIndex:t})},t.prototype.followActiveLink=function(){this.activeLinkAction&&this.activeLinkAction()},t.prototype.updateResults=function(){var e=this.input&&this.input.value||"",t={};this.state.fuse.search(e).forEach(function(e){var n=e.item.module;(t[n]||(t[n]=[])).push(e)});var n=[];for(var o in t)!function(e){var o=t[e],r=0;o.forEach(function(e){r+=1/e.score}),n.push({module:e,totalScore:1/r,items:o})}(o);n.sort(function(e,t){return e.totalScore-t.totalScore}),this.setState({searchString:e,isVisible:!0,moduleResults:n})},t.prototype.componentDidUpdate=function(){if(this.searchResults&&this.activeLink&&this.navigatedByKeyboard){var e=this.activeLink.getClientRects()[0],t=this.searchResults.getClientRects()[0].top;e.bottom>window.innerHeight?this.searchResults.scrollTop+=e.bottom-window.innerHeight+80:e.top<t&&(this.searchResults.scrollTop-=t-e.top+80)}this.focusPlease&&this.input&&this.input.focus(),this.navigatedByKeyboard=!1,this.focusPlease=!1},t.prototype.componentDidMount=function(){this.props.showHideTrigger(this.toggleVisibility.bind(this))},t.prototype.render=function(e,t){var n=this;if(t.failedLoading){var o="file:"==window.location.protocol;return d("div",{id:"search",class:t.isVisible?"":"hidden"},d("div",{id:"search-results"},d("p",{class:"error"},"Failed to load file 'doc-index.json' containing definitions in this package."),o?d("p",{class:"error"},"To use quick jump, load this page with HTTP (from a local static file web server) instead of using the ",d("code",null,"file://")," protocol. (For security reasons, it is not possible to fetch auxiliary files using JS in a HTML page opened with ",d("code",null,"file://"),".)"):[]))}this.linkIndex=0;var r=function(e){e.stopPropagation()},c=i(10,t.moduleResults).map(function(e){return n.renderResultsInModule(e)});return d("div",{id:"search",class:t.isVisible?"":"hidden"},d("div",{id:"search-form",onMouseDown:r},d("input",{placeholder:"Search in package by name",ref:function(e){n.input=e},onFocus:this.show.bind(this),onClick:this.show.bind(this),onInput:this.updateResults.bind(this)})),d("div",{id:"search-results",ref:function(e){n.searchResults=e},onMouseDown:r,onMouseOver:function(e){for(var t=e.target;t&&"function"==typeof t.getAttribute;){var o=t.getAttribute("data-link-index");if("string"==typeof o){var r=parseInt(o,10);n.setState({activeLinkIndex:r});break}t=t.parentNode}}},""===t.searchString?[d(a,null),d(s,null)]:0==c.length?d(l,{searchString:t.searchString}):d("ul",null,c)))},t.prototype.renderResultsInModule=function(e){var t=this,n=e.items,o=e.module,r=this.state.expanded[o]||n.length<=10,s=r?n:i(8,n),a=function(e){return d("li",{class:"search-result"},t.navigationLink(t.props.baseUrl+"/"+e.link,{},d(g,{html:e.display_html})))};return d("li",{class:"search-module"},d("h4",null,o),d("ul",null,s.map(function(e){return a(e.item)}),r?[]:d("li",{class:"more-results"},this.actionLink(function(){var e=Object.assign({},t.state.expanded);e[o]=!0,t.setState({expanded:e})},{},"show "+(n.length-s.length)+" more results from this module"))))},t.prototype.navigationLink=function(e,t){for(var n=this,o=[],r=2;r<arguments.length;r++)o[r-2]=arguments[r];var i=Object.assign({href:e,onClick:this.hide.bind(this)},t);return this.menuLink.apply(this,[i,function(){window.location.href=e,n.hide()}].concat(o))},t.prototype.actionLink=function(e,t){for(var n=[],o=2;o<arguments.length;o++)n[o-2]=arguments[o];var r=Object.assign({href:"#",onClick:function(t){t.preventDefault(),e()}},t);return this.menuLink.apply(this,[r,e].concat(n))},t.prototype.menuLink=function(e,t){for(var n=this,o=[],r=2;r<arguments.length;r++)o[r-2]=arguments[r];var i=this.linkIndex;i===this.state.activeLinkIndex&&(e.class=(e.class?e.class+" ":"")+"active-link",e.ref=function(e){e&&(n.activeLink=e)},this.activeLinkAction=t);var s=Object.assign({"data-link-index":i},e);return this.linkIndex+=1,d.apply(void 0,["a",s].concat(o))},t}(f),g=function(e){function t(){return null!==e&&e.apply(this,arguments)||this}return u(t,e),t.prototype.shouldComponentUpdate=function(e){return this.props.html!==e.html},t.prototype.render=function(e){return d("div",{dangerouslySetInnerHTML:{__html:e.html}})},t}(f);n.init=c,window.quickNav={init:c}},{"fuse.js":2,preact:3}],2:[function(e,t,n){!function(e,o){"object"==typeof n&&"object"==typeof t?t.exports=o():"function"==typeof define&&define.amd?define("Fuse",[],o):"object"==typeof n?n.Fuse=o():e.Fuse=o()}(this,function(){return function(e){function t(o){if(n[o])return n[o].exports;var r=n[o]={i:o,l:!1,exports:{}};return e[o].call(r.exports,r,r.exports,t),r.l=!0,r.exports}var n={};return t.m=e,t.c=n,t.i=function(e){return e},t.d=function(e,n,o){t.o(e,n)||Object.defineProperty(e,n,{configurable:!1,enumerable:!0,get:o})},t.n=function(e){var n=e&&e.__esModule?function(){return e.default}:function(){return e};return t.d(n,"a",n),n},t.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},t.p="",t(t.s=8)}([function(e,t,n){"use strict";e.exports=function(e){return"[object Array]"===Object.prototype.toString.call(e)}},function(e,t,n){"use strict";function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}var r=function(){function e(e,t){for(var n=0;n<t.length;n++){var o=t[n];o.enumerable=o.enumerable||!1,o.configurable=!0,"value"in o&&(o.writable=!0),Object.defineProperty(e,o.key,o)}}return function(t,n,o){return n&&e(t.prototype,n),o&&e(t,o),t}}(),i=n(5),s=n(7),a=n(4),l=function(){function e(t,n){var r=n.location,i=void 0===r?0:r,s=n.distance,l=void 0===s?100:s,c=n.threshold,u=void 0===c?.6:c,h=n.maxPatternLength,p=void 0===h?32:h,d=n.isCaseSensitive,f=void 0!==d&&d,v=n.tokenSeparator,_=void 0===v?/ +/g:v,g=n.findAllMatches,m=void 0!==g&&g,y=n.minMatchCharLength,k=void 0===y?1:y;o(this,e),this.options={location:i,distance:l,threshold:u,maxPatternLength:p,isCaseSensitive:f,tokenSeparator:_,findAllMatches:m,minMatchCharLength:k},this.pattern=this.options.isCaseSensitive?t:t.toLowerCase(),this.pattern.length<=p&&(this.patternAlphabet=a(this.pattern))}return r(e,[{key:"search",value:function(e){if(this.options.isCaseSensitive||(e=e.toLowerCase()),this.pattern===e)return{isMatch:!0,score:0,matchedIndices:[[0,e.length-1]]};var t=this.options,n=t.maxPatternLength,o=t.tokenSeparator;if(this.pattern.length>n)return i(e,this.pattern,o);var r=this.options,a=r.location,l=r.distance,c=r.threshold,u=r.findAllMatches,h=r.minMatchCharLength;return s(e,this.pattern,this.patternAlphabet,{location:a,distance:l,threshold:c,findAllMatches:u,minMatchCharLength:h})}}]),e}();e.exports=l},function(e,t,n){"use strict";var o=n(0),r=function e(t,n,r){if(n){var i=n.indexOf("."),s=n,a=null;-1!==i&&(s=n.slice(0,i),a=n.slice(i+1));var l=t[s];if(null!==l&&void 0!==l)if(a||"string"!=typeof l&&"number"!=typeof l)if(o(l))for(var c=0,u=l.length;c<u;c+=1)e(l[c],a,r);else a&&e(l,a,r);else r.push(l.toString())}else r.push(t);return r};e.exports=function(e,t){return r(e,t,[])}},function(e,t,n){"use strict";e.exports=function(){for(var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:[],t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:1,n=[],o=-1,r=-1,i=0,s=e.length;i<s;i+=1){var a=e[i];a&&-1===o?o=i:a||-1===o||((r=i-1)-o+1>=t&&n.push([o,r]),o=-1)}return e[i-1]&&i-o>=t&&n.push([o,i-1]),n}},function(e,t,n){"use strict";e.exports=function(e){for(var t={},n=e.length,o=0;o<n;o+=1)t[e.charAt(o)]=0;for(var r=0;r<n;r+=1)t[e.charAt(r)]|=1<<n-r-1;return t}},function(e,t,n){"use strict";var o=/[\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|]/g;e.exports=function(e,t){var n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:/ +/g,r=new RegExp(t.replace(o,"\\$&").replace(n,"|")),i=e.match(r),s=!!i,a=[];if(s)for(var l=0,c=i.length;l<c;l+=1){var u=i[l];a.push([e.indexOf(u),u.length-1])}return{score:s?.5:1,isMatch:s,matchedIndices:a}}},function(e,t,n){"use strict";e.exports=function(e,t){var n=t.errors,o=void 0===n?0:n,r=t.currentLocation,i=void 0===r?0:r,s=t.expectedLocation,a=void 0===s?0:s,l=t.distance,c=void 0===l?100:l,u=o/e.length,h=Math.abs(a-i);return c?u+h/c:h?1:u}},function(e,t,n){"use strict";var o=n(6),r=n(3);e.exports=function(e,t,n,i){for(var s=i.location,a=void 0===s?0:s,l=i.distance,c=void 0===l?100:l,u=i.threshold,h=void 0===u?.6:u,p=i.findAllMatches,d=void 0!==p&&p,f=i.minMatchCharLength,v=void 0===f?1:f,_=a,g=e.length,m=h,y=e.indexOf(t,_),k=t.length,b=[],x=0;x<g;x+=1)b[x]=0;if(-1!==y){var w=o(t,{errors:0,currentLocation:y,expectedLocation:_,distance:c});if(m=Math.min(w,m),-1!==(y=e.lastIndexOf(t,_+k))){var S=o(t,{errors:0,currentLocation:y,expectedLocation:_,distance:c});m=Math.min(S,m)}}y=-1;for(var L=[],C=1,M=k+g,N=1<<k-1,I=0;I<k;I+=1){for(var A=0,T=M;A<T;)o(t,{errors:I,currentLocation:_+T,expectedLocation:_,distance:c})<=m?A=T:M=T,T=Math.floor((M-A)/2+A);M=T;var O=Math.max(1,_-T+1),j=d?g:Math.min(_+T,g)+k,P=Array(j+2);P[j+1]=(1<<I)-1;for(var E=j;E>=O;E-=1){var R=E-1,U=n[e.charAt(R)];if(U&&(b[R]=1),P[E]=(P[E+1]<<1|1)&U,0!==I&&(P[E]|=(L[E+1]|L[E])<<1|1|L[E+1]),P[E]&N&&(C=o(t,{errors:I,currentLocation:R,expectedLocation:_,distance:c}))<=m){if(m=C,(y=R)<=_)break;O=Math.max(1,2*_-y)}}if(o(t,{errors:I+1,currentLocation:_,expectedLocation:_,distance:c})>m)break;L=P}return{isMatch:y>=0,score:0===C?.001:C,matchedIndices:r(b,v)}}},function(e,t,n){"use strict";function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}var r=function(){function e(e,t){for(var n=0;n<t.length;n++){var o=t[n];o.enumerable=o.enumerable||!1,o.configurable=!0,"value"in o&&(o.writable=!0),Object.defineProperty(e,o.key,o)}}return function(t,n,o){return n&&e(t.prototype,n),o&&e(t,o),t}}(),i=n(1),s=n(2),a=n(0),l=function(){function e(t,n){var r=n.location,i=void 0===r?0:r,a=n.distance,l=void 0===a?100:a,c=n.threshold,u=void 0===c?.6:c,h=n.maxPatternLength,p=void 0===h?32:h,d=n.caseSensitive,f=void 0!==d&&d,v=n.tokenSeparator,_=void 0===v?/ +/g:v,g=n.findAllMatches,m=void 0!==g&&g,y=n.minMatchCharLength,k=void 0===y?1:y,b=n.id,x=void 0===b?null:b,w=n.keys,S=void 0===w?[]:w,L=n.shouldSort,C=void 0===L||L,M=n.getFn,N=void 0===M?s:M,I=n.sortFn,A=void 0===I?function(e,t){return e.score-t.score}:I,T=n.tokenize,O=void 0!==T&&T,j=n.matchAllTokens,P=void 0!==j&&j,E=n.includeMatches,R=void 0!==E&&E,U=n.includeScore,D=void 0!==U&&U,V=n.verbose,F=void 0!==V&&V;o(this,e),this.options={location:i,distance:l,threshold:u,maxPatternLength:p,isCaseSensitive:f,tokenSeparator:_,findAllMatches:m,minMatchCharLength:k,id:x,keys:S,includeMatches:R,includeScore:D,shouldSort:C,getFn:N,sortFn:A,verbose:F,tokenize:O,matchAllTokens:P},this.setCollection(t)}return r(e,[{key:"setCollection",value:function(e){return this.list=e,e}},{key:"search",value:function(e){this._log('---------\nSearch pattern: "'+e+'"');var t=this._prepareSearchers(e),n=t.tokenSearchers,o=t.fullSearcher,r=this._search(n,o),i=r.weights,s=r.results;return this._computeScore(i,s),this.options.shouldSort&&this._sort(s),this._format(s)}},{key:"_prepareSearchers",value:function(){var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:"",t=[];if(this.options.tokenize)for(var n=e.split(this.options.tokenSeparator),o=0,r=n.length;o<r;o+=1)t.push(new i(n[o],this.options));return{tokenSearchers:t,fullSearcher:new i(e,this.options)}}},{key:"_search",value:function(){var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:[],t=arguments[1],n=this.list,o={},r=[];if("string"==typeof n[0]){for(var i=0,s=n.length;i<s;i+=1)this._analyze({key:"",value:n[i],record:i,index:i},{resultMap:o,results:r,tokenSearchers:e,fullSearcher:t});return{weights:null,results:r}}for(var a={},l=0,c=n.length;l<c;l+=1)for(var u=n[l],h=0,p=this.options.keys.length;h<p;h+=1){var d=this.options.keys[h];if("string"!=typeof d){if(a[d.name]={weight:1-d.weight||1},d.weight<=0||d.weight>1)throw new Error("Key weight has to be > 0 and <= 1");d=d.name}else a[d]={weight:1};this._analyze({key:d,value:this.options.getFn(u,d),record:u,index:l},{resultMap:o,results:r,tokenSearchers:e,fullSearcher:t})}return{weights:a,results:r}}},{key:"_analyze",value:function(e,t){var n=e.key,o=e.arrayIndex,r=void 0===o?-1:o,i=e.value,s=e.record,l=e.index,c=t.tokenSearchers,u=void 0===c?[]:c,h=t.fullSearcher,p=void 0===h?[]:h,d=t.resultMap,f=void 0===d?{}:d,v=t.results,_=void 0===v?[]:v;if(void 0!==i&&null!==i){var g=!1,m=-1,y=0;if("string"==typeof i){this._log("\nKey: "+(""===n?"-":n));var k=p.search(i);if(this._log('Full text: "'+i+'", score: '+k.score),this.options.tokenize){for(var b=i.split(this.options.tokenSeparator),x=[],w=0;w<u.length;w+=1){var S=u[w];this._log('\nPattern: "'+S.pattern+'"');for(var L=!1,C=0;C<b.length;C+=1){var M=b[C],N=S.search(M),I={};N.isMatch?(I[M]=N.score,g=!0,L=!0,x.push(N.score)):(I[M]=1,this.options.matchAllTokens||x.push(1)),this._log('Token: "'+M+'", score: '+I[M])}L&&(y+=1)}m=x[0];for(var A=x.length,T=1;T<A;T+=1)m+=x[T];m/=A,this._log("Token score average:",m)}var O=k.score;m>-1&&(O=(O+m)/2),this._log("Score average:",O);var j=!this.options.tokenize||!this.options.matchAllTokens||y>=u.length;if(this._log("\nCheck Matches: "+j),(g||k.isMatch)&&j){var P=f[l];P?P.output.push({key:n,arrayIndex:r,value:i,score:O,matchedIndices:k.matchedIndices}):(f[l]={item:s,output:[{key:n,arrayIndex:r,value:i,score:O,matchedIndices:k.matchedIndices}]},_.push(f[l]))}}else if(a(i))for(var E=0,R=i.length;E<R;E+=1)this._analyze({key:n,arrayIndex:E,value:i[E],record:s,index:l},{resultMap:f,results:_,tokenSearchers:u,fullSearcher:p})}}},{key:"_computeScore",value:function(e,t){this._log("\n\nComputing score:\n");for(var n=0,o=t.length;n<o;n+=1){for(var r=t[n].output,i=r.length,s=0,a=1,l=0;l<i;l+=1){var c=r[l].score,u=e?e[r[l].key].weight:1,h=c*u;1!==u?a=Math.min(a,h):(r[l].nScore=h,s+=h)}t[n].score=1===a?s/i:a,this._log(t[n])}}},{key:"_sort",value:function(e){this._log("\n\nSorting...."),e.sort(this.options.sortFn)}},{key:"_format",value:function(e){var t=[];this._log("\n\nOutput:\n\n",JSON.stringify(e));var n=[];this.options.includeMatches&&n.push(function(e,t){var n=e.output;t.matches=[];for(var o=0,r=n.length;o<r;o+=1){var i=n[o];if(0!==i.matchedIndices.length){var s={indices:i.matchedIndices,value:i.value};i.key&&(s.key=i.key),i.hasOwnProperty("arrayIndex")&&i.arrayIndex>-1&&(s.arrayIndex=i.arrayIndex),t.matches.push(s)}}}),this.options.includeScore&&n.push(function(e,t){t.score=e.score});for(var o=0,r=e.length;o<r;o+=1){var i=e[o];if(this.options.id&&(i.item=this.options.getFn(i.item,this.options.id)[0]),n.length){for(var s={item:i.item},a=0,l=n.length;a<l;a+=1)n[a](i,s);t.push(s)}else t.push(i.item)}return t}},{key:"_log",value:function(){if(this.options.verbose){var e;(e=console).log.apply(e,arguments)}}}]),e}();e.exports=l}])})},{}],3:[function(e,t,n){!function(){"use strict";function e(){}function n(t,n){var o,r,i,s,a=T;for(s=arguments.length;s-- >2;)A.push(arguments[s]);for(n&&null!=n.children&&(A.length||A.push(n.children),delete n.children);A.length;)if((r=A.pop())&&void 0!==r.pop)for(s=r.length;s--;)A.push(r[s]);else"boolean"==typeof r&&(r=null),(i="function"!=typeof t)&&(null==r?r="":"number"==typeof r?r=String(r):"string"!=typeof r&&(i=!1)),i&&o?a[a.length-1]+=r:a===T?a=[r]:a.push(r),o=i;var l=new e;return l.nodeName=t,l.children=a,l.attributes=null==n?void 0:n,l.key=null==n?void 0:n.key,void 0!==I.vnode&&I.vnode(l),l}function o(e,t){for(var n in t)e[n]=t[n];return e}function r(e){!e.__d&&(e.__d=!0)&&1==P.push(e)&&(I.debounceRendering||O)(i)}function i(){var e,t=P;for(P=[];e=t.pop();)e.__d&&L(e)}function s(e,t,n){return"string"==typeof t||"number"==typeof t?void 0!==e.splitText:"string"==typeof t.nodeName?!e._componentConstructor&&a(e,t.nodeName):n||e._componentConstructor===t.nodeName}function a(e,t){return e.__n===t||e.nodeName.toLowerCase()===t.toLowerCase()}function l(e){var t=o({},e.attributes);t.children=e.children;var n=e.nodeName.defaultProps;if(void 0!==n)for(var r in n)void 0===t[r]&&(t[r]=n[r]);return t}function c(e,t){var n=t?document.createElementNS("http://www.w3.org/2000/svg",e):document.createElement(e);return n.__n=e,n}function u(e){var t=e.parentNode;t&&t.removeChild(e)}function h(e,t,n,o,r){if("className"===t&&(t="class"),"key"===t);else if("ref"===t)n&&n(null),o&&o(e);else if("class"!==t||r)if("style"===t){if(o&&"string"!=typeof o&&"string"!=typeof n||(e.style.cssText=o||""),o&&"object"==typeof o){if("string"!=typeof n)for(var i in n)i in o||(e.style[i]="");for(var i in o)e.style[i]="number"==typeof o[i]&&!1===j.test(i)?o[i]+"px":o[i]}}else if("dangerouslySetInnerHTML"===t)o&&(e.innerHTML=o.__html||"");else if("o"==t[0]&&"n"==t[1]){var s=t!==(t=t.replace(/Capture$/,""));t=t.toLowerCase().substring(2),o?n||e.addEventListener(t,d,s):e.removeEventListener(t,d,s),(e.__l||(e.__l={}))[t]=o}else if("list"!==t&&"type"!==t&&!r&&t in e)p(e,t,null==o?"":o),null!=o&&!1!==o||e.removeAttribute(t);else{var a=r&&t!==(t=t.replace(/^xlink\:?/,""));null==o||!1===o?a?e.removeAttributeNS("http://www.w3.org/1999/xlink",t.toLowerCase()):e.removeAttribute(t):"function"!=typeof o&&(a?e.setAttributeNS("http://www.w3.org/1999/xlink",t.toLowerCase(),o):e.setAttribute(t,o))}else e.className=o||""}function p(e,t,n){try{e[t]=n}catch(e){}}function d(e){return this.__l[e.type](I.event&&I.event(e)||e)}function f(){for(var e;e=E.pop();)I.afterMount&&I.afterMount(e),e.componentDidMount&&e.componentDidMount()}function v(e,t,n,o,r,i){R++||(U=null!=r&&void 0!==r.ownerSVGElement,D=null!=e&&!("__preactattr_"in e));var s=_(e,t,n,o,i);return r&&s.parentNode!==r&&r.appendChild(s),--R||(D=!1,i||f()),s}function _(e,t,n,o,r){var i=e,s=U;if(null!=t&&"boolean"!=typeof t||(t=""),"string"==typeof t||"number"==typeof t)return e&&void 0!==e.splitText&&e.parentNode&&(!e._component||r)?e.nodeValue!=t&&(e.nodeValue=t):(i=document.createTextNode(t),e&&(e.parentNode&&e.parentNode.replaceChild(i,e),m(e,!0))),i.__preactattr_=!0,i;var l=t.nodeName;if("function"==typeof l)return C(e,t,n,o);if(U="svg"===l||"foreignObject"!==l&&U,l=String(l),(!e||!a(e,l))&&(i=c(l,U),e)){for(;e.firstChild;)i.appendChild(e.firstChild);e.parentNode&&e.parentNode.replaceChild(i,e),m(e,!0)}var u=i.firstChild,h=i.__preactattr_,p=t.children;if(null==h){h=i.__preactattr_={};for(var d=i.attributes,f=d.length;f--;)h[d[f].name]=d[f].value}return!D&&p&&1===p.length&&"string"==typeof p[0]&&null!=u&&void 0!==u.splitText&&null==u.nextSibling?u.nodeValue!=p[0]&&(u.nodeValue=p[0]):(p&&p.length||null!=u)&&g(i,p,n,o,D||null!=h.dangerouslySetInnerHTML),k(i,t.attributes,h),U=s,i}function g(e,t,n,o,r){var i,a,l,c,h,p=e.childNodes,d=[],f={},v=0,g=0,y=p.length,k=0,b=t?t.length:0;if(0!==y)for(L=0;L<y;L++){var x=p[L],w=x.__preactattr_;null!=(S=b&&w?x._component?x._component.__k:w.key:null)?(v++,f[S]=x):(w||(void 0!==x.splitText?!r||x.nodeValue.trim():r))&&(d[k++]=x)}if(0!==b)for(L=0;L<b;L++){h=null;var S=(c=t[L]).key;if(null!=S)v&&void 0!==f[S]&&(h=f[S],f[S]=void 0,v--);else if(!h&&g<k)for(i=g;i<k;i++)if(void 0!==d[i]&&s(a=d[i],c,r)){h=a,d[i]=void 0,i===k-1&&k--,i===g&&g++;break}h=_(h,c,n,o),l=p[L],h&&h!==e&&h!==l&&(null==l?e.appendChild(h):h===l.nextSibling?u(l):e.insertBefore(h,l))}if(v)for(var L in f)void 0!==f[L]&&m(f[L],!1);for(;g<=k;)void 0!==(h=d[k--])&&m(h,!1)}function m(e,t){var n=e._component;n?M(n):(null!=e.__preactattr_&&e.__preactattr_.ref&&e.__preactattr_.ref(null),!1!==t&&null!=e.__preactattr_||u(e),y(e))}function y(e){for(e=e.lastChild;e;){var t=e.previousSibling;m(e,!0),e=t}}function k(e,t,n){var o;for(o in n)t&&null!=t[o]||null==n[o]||h(e,o,n[o],n[o]=void 0,U);for(o in t)"children"===o||"innerHTML"===o||o in n&&t[o]===("value"===o||"checked"===o?e[o]:n[o])||h(e,o,n[o],n[o]=t[o],U)}function b(e){var t=e.constructor.name;(V[t]||(V[t]=[])).push(e)}function x(e,t,n){var o,r=V[e.name];if(e.prototype&&e.prototype.render?(o=new e(t,n),N.call(o,t,n)):((o=new N(t,n)).constructor=e,o.render=w),r)for(var i=r.length;i--;)if(r[i].constructor===e){o.__b=r[i].__b,r.splice(i,1);break}return o}function w(e,t,n){return this.constructor(e,n)}function S(e,t,n,o,i){e.__x||(e.__x=!0,(e.__r=t.ref)&&delete t.ref,(e.__k=t.key)&&delete t.key,!e.base||i?e.componentWillMount&&e.componentWillMount():e.componentWillReceiveProps&&e.componentWillReceiveProps(t,o),o&&o!==e.context&&(e.__c||(e.__c=e.context),e.context=o),e.__p||(e.__p=e.props),e.props=t,e.__x=!1,0!==n&&(1!==n&&!1===I.syncComponentUpdates&&e.base?r(e):L(e,1,i)),e.__r&&e.__r(e))}function L(e,t,n,r){if(!e.__x){var i,s,a,c=e.props,u=e.state,h=e.context,p=e.__p||c,d=e.__s||u,_=e.__c||h,g=e.base,y=e.__b,k=g||y,b=e._component,w=!1;if(g&&(e.props=p,e.state=d,e.context=_,2!==t&&e.shouldComponentUpdate&&!1===e.shouldComponentUpdate(c,u,h)?w=!0:e.componentWillUpdate&&e.componentWillUpdate(c,u,h),e.props=c,e.state=u,e.context=h),e.__p=e.__s=e.__c=e.__b=null,e.__d=!1,!w){i=e.render(c,u,h),e.getChildContext&&(h=o(o({},h),e.getChildContext()));var C,N,A=i&&i.nodeName;if("function"==typeof A){var T=l(i);(s=b)&&s.constructor===A&&T.key==s.__k?S(s,T,1,h,!1):(C=s,e._component=s=x(A,T,h),s.__b=s.__b||y,s.__u=e,S(s,T,0,h,!1),L(s,1,n,!0)),N=s.base}else a=k,(C=b)&&(a=e._component=null),(k||1===t)&&(a&&(a._component=null),N=v(a,i,h,n||!g,k&&k.parentNode,!0));if(k&&N!==k&&s!==b){var O=k.parentNode;O&&N!==O&&(O.replaceChild(N,k),C||(k._component=null,m(k,!1)))}if(C&&M(C),e.base=N,N&&!r){for(var j=e,P=e;P=P.__u;)(j=P).base=N;N._component=j,N._componentConstructor=j.constructor}}if(!g||n?E.unshift(e):w||(e.componentDidUpdate&&e.componentDidUpdate(p,d,_),I.afterUpdate&&I.afterUpdate(e)),null!=e.__h)for(;e.__h.length;)e.__h.pop().call(e);R||r||f()}}function C(e,t,n,o){for(var r=e&&e._component,i=r,s=e,a=r&&e._componentConstructor===t.nodeName,c=a,u=l(t);r&&!c&&(r=r.__u);)c=r.constructor===t.nodeName;return r&&c&&(!o||r._component)?(S(r,u,3,n,o),e=r.base):(i&&!a&&(M(i),e=s=null),r=x(t.nodeName,u,n),e&&!r.__b&&(r.__b=e,s=null),S(r,u,1,n,o),e=r.base,s&&e!==s&&(s._component=null,m(s,!1))),e}function M(e){I.beforeUnmount&&I.beforeUnmount(e);var t=e.base;e.__x=!0,e.componentWillUnmount&&e.componentWillUnmount(),e.base=null;var n=e._component;n?M(n):t&&(t.__preactattr_&&t.__preactattr_.ref&&t.__preactattr_.ref(null),e.__b=t,u(t),b(e),y(t)),e.__r&&e.__r(null)}function N(e,t){this.__d=!0,this.context=t,this.props=e,this.state=this.state||{}}var I={},A=[],T=[],O="function"==typeof Promise?Promise.resolve().then.bind(Promise.resolve()):setTimeout,j=/acit|ex(?:s|g|n|p|$)|rph|ows|mnc|ntw|ine[ch]|zoo|^ord/i,P=[],E=[],R=0,U=!1,D=!1,V={};o(N.prototype,{setState:function(e,t){var n=this.state;this.__s||(this.__s=o({},n)),o(n,"function"==typeof e?e(n,this.props):e),t&&(this.__h=this.__h||[]).push(t),r(this)},forceUpdate:function(e){e&&(this.__h=this.__h||[]).push(e),L(this,2)},render:function(){}});var F={h:n,createElement:n,cloneElement:function(e,t){return n(e.nodeName,o(o({},e.attributes),t),arguments.length>2?[].slice.call(arguments,2):e.children)},Component:N,render:function(e,t,n){return v(n,e,{},!1,t,!1)},rerender:i,options:I};void 0!==t?t.exports=F:self.preact=F}()},{}]},{},[1]); //# sourceMappingURL=quick-jump.min.js.map diff --git a/haddock-api/src/Haddock.hs b/haddock-api/src/Haddock.hs index f7fa52b3..00eb50f6 100644 --- a/haddock-api/src/Haddock.hs +++ b/haddock-api/src/Haddock.hs @@ -1,5 +1,5 @@ {-# OPTIONS_GHC -Wwarn #-} -{-# LANGUAGE CPP, ScopedTypeVariables, Rank2Types #-} +{-# LANGUAGE CPP, ScopedTypeVariables, OverloadedStrings, Rank2Types #-} {-# LANGUAGE LambdaCase #-} ----------------------------------------------------------------------------- -- | @@ -25,7 +25,6 @@ module Haddock ( withGhc ) where -import Data.Version import Haddock.Backends.Xhtml import Haddock.Backends.Xhtml.Meta import Haddock.Backends.Xhtml.Themes (getThemes) @@ -42,7 +41,6 @@ import Haddock.Options import Haddock.Utils import Control.Monad hiding (forM_) -import Control.Applicative import Data.Foldable (forM_, foldl') import Data.Traversable (for) import Data.List (isPrefixOf) @@ -151,7 +149,8 @@ haddockWithGhc ghc args = handleTopExceptions $ do -- or which exits with an error or help message. (flags, files) <- parseHaddockOpts args shortcutFlags flags - qual <- case qualification flags of {Left msg -> throwE msg; Right q -> return q} + qual <- rightOrThrowE (qualification flags) + sinceQual <- rightOrThrowE (sinceQualification flags) -- inject dynamic-too into flags before we proceed flags' <- ghc flags $ do @@ -184,7 +183,7 @@ haddockWithGhc ghc args = handleTopExceptions $ do } -- Render the interfaces. - liftIO $ renderStep dflags flags qual packages ifaces + liftIO $ renderStep dflags flags sinceQual qual packages ifaces else do when (any (`elem` [Flag_Html, Flag_Hoogle, Flag_LaTeX]) flags) $ @@ -194,7 +193,7 @@ haddockWithGhc ghc args = handleTopExceptions $ do packages <- liftIO $ readInterfaceFiles freshNameCache (readIfaceArgs flags) -- Render even though there are no input files (usually contents/index). - liftIO $ renderStep dflags flags qual packages [] + liftIO $ renderStep dflags flags sinceQual qual packages [] -- | Create warnings about potential misuse of -optghc warnings :: [String] -> [String] @@ -228,8 +227,9 @@ readPackagesAndProcessModules flags files = do return (packages, ifaces, homeLinks) -renderStep :: DynFlags -> [Flag] -> QualOption -> [(DocPaths, InterfaceFile)] -> [Interface] -> IO () -renderStep dflags flags qual pkgs interfaces = do +renderStep :: DynFlags -> [Flag] -> SinceQual -> QualOption + -> [(DocPaths, InterfaceFile)] -> [Interface] -> IO () +renderStep dflags flags sinceQual nameQual pkgs interfaces = do updateHTMLXRefs pkgs let ifaceFiles = map snd pkgs @@ -238,12 +238,12 @@ renderStep dflags flags qual pkgs interfaces = do ((_, Just path), ifile) <- pkgs iface <- ifInstalledIfaces ifile return (instMod iface, path) - render dflags flags qual interfaces installedIfaces extSrcMap - + render dflags flags sinceQual nameQual interfaces installedIfaces extSrcMap -- | Render the interfaces with whatever backend is specified in the flags. -render :: DynFlags -> [Flag] -> QualOption -> [Interface] -> [InstalledInterface] -> Map Module FilePath -> IO () -render dflags flags qual ifaces installedIfaces extSrcMap = do +render :: DynFlags -> [Flag] -> SinceQual -> QualOption -> [Interface] + -> [InstalledInterface] -> Map Module FilePath -> IO () +render dflags flags sinceQual qual ifaces installedIfaces extSrcMap = do let title = fromMaybe "" (optTitle flags) @@ -270,6 +270,10 @@ render dflags flags qual ifaces installedIfaces extSrcMap = do pkgKey = moduleUnitId pkgMod pkgStr = Just (unitIdString pkgKey) pkgNameVer = modulePackageInfo dflags flags pkgMod + pkgName = fmap (unpackFS . (\(PackageName n) -> n)) (fst pkgNameVer) + sincePkg = case sinceQual of + External -> pkgName + Always -> Nothing (srcBase, srcModule, srcEntity, srcLEntity) = sourceUrls flags @@ -277,7 +281,7 @@ render dflags flags qual ifaces installedIfaces extSrcMap = do | Flag_HyperlinkedSource `elem` flags = Just hypSrcModuleUrlFormat | otherwise = srcModule - srcMap = mkSrcMap $ Map.union + srcMap = Map.union (Map.map SrcExternal extSrcMap) (Map.fromList [ (ifaceMod iface, SrcLocal) | iface <- ifaces ]) @@ -323,24 +327,34 @@ render dflags flags qual ifaces installedIfaces extSrcMap = do let withQuickjump = Flag_QuickJumpIndex `elem` flags when (Flag_GenIndex `elem` flags) $ do - ppHtmlIndex odir title pkgStr - themes opt_mathjax opt_contents_url sourceUrls' opt_wiki_urls - allVisibleIfaces pretty + withTiming (pure dflags') "ppHtmlIndex" (const ()) $ do + _ <- {-# SCC ppHtmlIndex #-} + ppHtmlIndex odir title pkgStr + themes opt_mathjax opt_contents_url sourceUrls' opt_wiki_urls + allVisibleIfaces pretty + return () + copyHtmlBits odir libDir themes withQuickjump when (Flag_GenContents `elem` flags) $ do - ppHtmlContents dflags' odir title pkgStr - themes opt_mathjax opt_index_url sourceUrls' opt_wiki_urls - allVisibleIfaces True prologue pretty - (makeContentsQual qual) + withTiming (pure dflags') "ppHtmlContents" (const ()) $ do + _ <- {-# SCC ppHtmlContents #-} + ppHtmlContents dflags' odir title pkgStr + themes opt_mathjax opt_index_url sourceUrls' opt_wiki_urls + allVisibleIfaces True prologue pretty + sincePkg (makeContentsQual qual) + return () copyHtmlBits odir libDir themes withQuickjump when (Flag_Html `elem` flags) $ do - ppHtml dflags' title pkgStr visibleIfaces reexportedIfaces odir - prologue - themes opt_mathjax sourceUrls' opt_wiki_urls - opt_contents_url opt_index_url unicode qual - pretty withQuickjump + withTiming (pure dflags') "ppHtml" (const ()) $ do + _ <- {-# SCC ppHtml #-} + ppHtml dflags' title pkgStr visibleIfaces reexportedIfaces odir + prologue + themes opt_mathjax sourceUrls' opt_wiki_urls + opt_contents_url opt_index_url unicode sincePkg qual + pretty withQuickjump + return () copyHtmlBits odir libDir themes withQuickjump writeHaddockMeta odir withQuickjump @@ -348,7 +362,12 @@ render dflags flags qual ifaces installedIfaces extSrcMap = do -- might want to fix that if/when these two get some work on them when (Flag_Hoogle `elem` flags) $ do case pkgNameVer of - Nothing -> putStrLn . unlines $ + (Just (PackageName pkgNameFS), Just pkgVer) -> + let pkgNameStr | unpackFS pkgNameFS == "main" && title /= [] = title + | otherwise = unpackFS pkgNameFS + in ppHoogle dflags' pkgNameStr pkgVer title (fmap _doc prologue) + visibleIfaces odir + _ -> putStrLn . unlines $ [ "haddock: Unable to find a package providing module " ++ moduleNameString (moduleName pkgMod) ++ ", skipping Hoogle." , "" @@ -356,38 +375,19 @@ render dflags flags qual ifaces installedIfaces extSrcMap = do ++ " using the --package-name" , " and --package-version arguments." ] - Just (PackageName pkgNameFS, pkgVer) -> - let pkgNameStr | unpackFS pkgNameFS == "main" && title /= [] = title - | otherwise = unpackFS pkgNameFS - in ppHoogle dflags' pkgNameStr pkgVer title (fmap _doc prologue) - visibleIfaces odir when (Flag_LaTeX `elem` flags) $ do - ppLaTeX title pkgStr visibleIfaces odir (fmap _doc prologue) opt_latex_style - libDir + withTiming (pure dflags') "ppLatex" (const ()) $ do + _ <- {-# SCC ppLatex #-} + ppLaTeX title pkgStr visibleIfaces odir (fmap _doc prologue) opt_latex_style + libDir + return () when (Flag_HyperlinkedSource `elem` flags && not (null ifaces)) $ do - ppHyperlinkedSource odir libDir opt_source_css pretty srcMap ifaces - --- | From GHC 7.10, this function has a potential to crash with a --- nasty message such as @expectJust getPackageDetails@ because --- package name and versions can no longer reliably be extracted in --- all cases: if the package is not installed yet then this info is no --- longer available. The @--package-name@ and @--package-version@ --- Haddock flags allow the user to specify this information and it is --- returned here if present: if it is not present, the error will --- occur. Nasty but that's how it is for now. Potential TODO. -modulePackageInfo :: DynFlags - -> [Flag] -- ^ Haddock flags are checked as they may - -- contain the package name or version - -- provided by the user which we - -- prioritise - -> Module -> Maybe (PackageName, Data.Version.Version) -modulePackageInfo dflags flags modu = - cmdline <|> pkgDb - where - cmdline = (,) <$> optPackageName flags <*> optPackageVersion flags - pkgDb = (\pkg -> (packageName pkg, packageVersion pkg)) <$> lookupPackage dflags (moduleUnitId modu) + withTiming (pure dflags') "ppHyperlinkedSource" (const ()) $ do + _ <- {-# SCC ppHyperlinkedSource #-} + ppHyperlinkedSource odir libDir opt_source_css pretty srcMap ifaces + return () ------------------------------------------------------------------------------- @@ -400,7 +400,7 @@ readInterfaceFiles :: MonadIO m -> [(DocPaths, FilePath)] -> m [(DocPaths, InterfaceFile)] readInterfaceFiles name_cache_accessor pairs = do - catMaybes `liftM` mapM tryReadIface pairs + catMaybes `liftM` mapM ({-# SCC readInterfaceFile #-} tryReadIface) pairs where -- try to read an interface, warn if we can't tryReadIface (paths, file) = @@ -439,13 +439,26 @@ withGhc' libDir flags ghcActs = runGhc (Just libDir) $ do _ <- setSessionDynFlags dynflags'' ghcActs dynflags'' where + + -- ignore sublists of flags that start with "+RTS" and end in "-RTS" + -- + -- See https://github.com/haskell/haddock/issues/666 + filterRtsFlags :: [String] -> [String] + filterRtsFlags flgs = foldr go (const []) flgs True + where go "-RTS" func _ = func True + go "+RTS" func _ = func False + go _ func False = func False + go arg func True = arg : func True + + parseGhcFlags :: MonadIO m => DynFlags -> m DynFlags parseGhcFlags dynflags = do -- TODO: handle warnings? - (dynflags', rest, _) <- parseDynamicFlags dynflags (map noLoc flags) + let flags' = filterRtsFlags flags + (dynflags', rest, _) <- parseDynamicFlags dynflags (map noLoc flags') if not (null rest) - then throwE ("Couldn't parse GHC options: " ++ unwords flags) + then throwE ("Couldn't parse GHC options: " ++ unwords flags') else return dynflags' unsetPatternMatchWarnings :: DynFlags -> DynFlags @@ -596,10 +609,15 @@ getPrologue dflags flags = h <- openFile filename ReadMode hSetEncoding h utf8 str <- hGetContents h -- semi-closes the handle - return . Just $! parseParas dflags str + return . Just $! parseParas dflags Nothing str _ -> throwE "multiple -p/--prologue options" +rightOrThrowE :: Either String b -> IO b +rightOrThrowE (Left msg) = throwE msg +rightOrThrowE (Right x) = pure x + + #ifdef IN_GHC_TREE getInTreeDir :: IO String diff --git a/haddock-api/src/Haddock/Backends/Hoogle.hs b/haddock-api/src/Haddock/Backends/Hoogle.hs index c6139f12..257a8d6d 100644 --- a/haddock-api/src/Haddock/Backends/Hoogle.hs +++ b/haddock-api/src/Haddock/Backends/Hoogle.hs @@ -128,6 +128,7 @@ ppExport dflags ExportDecl { expItemDecl = L _ decl f (TyClD _ d@DataDecl{}) = ppData dflags d subdocs f (TyClD _ d@SynDecl{}) = ppSynonym dflags d f (TyClD _ d@ClassDecl{}) = ppClass dflags d subdocs + f (TyClD _ (FamDecl _ d)) = ppFam dflags d f (ForD _ (ForeignImport _ name typ _)) = [pp_sig dflags [name] (hsSigType typ)] f (ForD _ (ForeignExport _ name typ _)) = [pp_sig dflags [name] (hsSigType typ)] f (SigD _ sig) = ppSig dflags sig ++ ppFixities @@ -140,11 +141,7 @@ ppSigWithDoc :: DynFlags -> Sig GhcRn -> [(Name, DocForDecl Name)] -> [String] ppSigWithDoc dflags (TypeSig _ names sig) subdocs = concatMap mkDocSig names where - mkDocSig n = concatMap (ppDocumentation dflags) (getDoc n) - ++ [pp_sig dflags names (hsSigWcType sig)] - - getDoc :: Located Name -> [Documentation Name] - getDoc n = maybe [] (return . fst) (lookup (unL n) subdocs) + mkDocSig n = mkSubdoc dflags n subdocs [pp_sig dflags [n] (hsSigWcType sig)] ppSigWithDoc _ _ _ = [] @@ -172,10 +169,14 @@ ppClass dflags decl subdocs = ppTyFams | null $ tcdATs decl = "" | otherwise = (" " ++) . showSDocUnqual dflags . whereWrapper $ concat - [ map ppr (tcdATs decl) + [ map pprTyFam (tcdATs decl) , map (ppr . tyFamEqnToSyn . unLoc) (tcdATDefs decl) ] + pprTyFam :: LFamilyDecl GhcRn -> SDoc + pprTyFam (L _ at) = vcat' $ map text $ + mkSubdoc dflags (fdLName at) subdocs (ppFam dflags at) + whereWrapper elems = vcat' [ text "where" <+> lbrace , nest 4 . vcat . map (Outputable.<> semi) $ elems @@ -191,6 +192,16 @@ ppClass dflags decl subdocs = , tcdSExt = emptyNameSet } +ppFam :: DynFlags -> FamilyDecl GhcRn -> [String] +ppFam dflags decl@(FamilyDecl { fdInfo = info }) + = [out dflags decl'] + where + decl' = case info of + -- We don't need to print out a closed type family's equations + -- for Hoogle, so pretend it doesn't have any. + ClosedTypeFamily{} -> decl { fdInfo = OpenTypeFamily } + _ -> decl +ppFam _ XFamilyDecl {} = panic "ppFam" ppInstance :: DynFlags -> ClsInst -> [String] ppInstance dflags x = @@ -213,13 +224,12 @@ ppData dflags decl@(DataDecl { tcdDataDefn = defn }) subdocs concatMap (ppCtor dflags decl subdocs . unL) (dd_cons defn) where - -- GHC gives out "data Bar =", we want to delete the equals - -- also writes data : a b, when we want data (:) a b - showData d = unwords $ map f $ if last xs == "=" then init xs else xs + -- GHC gives out "data Bar =", we want to delete the equals. + -- There's no need to worry about parenthesizing infix data type names, + -- since this Outputable instance for TyClDecl gets this right already. + showData d = unwords $ if last xs == "=" then init xs else xs where xs = words $ out dflags d - nam = out dflags $ tyClDeclLName d - f w = if w == nam then operator nam else w ppData _ _ _ = panic "ppData" -- | for constructors, and named-fields... @@ -285,6 +295,10 @@ docWith dflags header d lines header ++ ["" | header /= "" && isJust d] ++ maybe [] (showTags . markup (markupTag dflags)) d +mkSubdoc :: DynFlags -> Located Name -> [(Name, DocForDecl Name)] -> [String] -> [String] +mkSubdoc dflags n subdocs s = concatMap (ppDocumentation dflags) getDoc ++ s + where + getDoc = maybe [] (return . fst) (lookup (unL n) subdocs) data Tag = TagL Char [Tags] | TagP Tags | TagPre Tags | TagInline String Tags | Str String deriving Show @@ -328,7 +342,8 @@ markupTag dflags = Markup { markupAName = const $ str "", markupProperty = box TagPre . str, markupExample = box TagPre . str . unlines . map exampleToString, - markupHeader = \(Header l h) -> box (TagInline $ "h" ++ show l) h + markupHeader = \(Header l h) -> box (TagInline $ "h" ++ show l) h, + markupTable = \(Table _ _) -> str "TODO: table" } diff --git a/haddock-api/src/Haddock/Backends/Hyperlinker/Ast.hs b/haddock-api/src/Haddock/Backends/Hyperlinker/Ast.hs index 56137f51..0ecf7109 100644 --- a/haddock-api/src/Haddock/Backends/Hyperlinker/Ast.hs +++ b/haddock-api/src/Haddock/Backends/Hyperlinker/Ast.hs @@ -12,6 +12,7 @@ import qualified Haddock.Syb as Syb import Haddock.Backends.Hyperlinker.Types import qualified GHC +import qualified SrcLoc import qualified Outputable as GHC import Control.Applicative @@ -52,10 +53,10 @@ type DetailsMap = Map.Map Position (Span, TokenDetails) mkDetailsMap :: [(GHC.SrcSpan, TokenDetails)] -> DetailsMap mkDetailsMap xs = - Map.fromListWith select_details [ (start, (token_span, token_details)) + Map.fromListWith select_details [ (start, (span, token_details)) | (ghc_span, token_details) <- xs - , Just !token_span <- [ghcSrcSpanToSpan ghc_span] - , let start = spStart token_span + , GHC.RealSrcSpan span <- [ghc_span] + , let start = SrcLoc.realSrcSpanStart span ] where -- favour token details which appear earlier in the list @@ -63,17 +64,11 @@ mkDetailsMap xs = lookupBySpan :: Span -> DetailsMap -> Maybe TokenDetails lookupBySpan span details = do - (_, (tok_span, tok_details)) <- Map.lookupLE (spStart span) details - guard (tok_span `containsSpan` span ) + let pos = SrcLoc.realSrcSpanStart span + (_, (tok_span, tok_details)) <- Map.lookupLE pos details + guard (tok_span `SrcLoc.containsSpan` span) return tok_details -ghcSrcSpanToSpan :: GHC.SrcSpan -> Maybe Span -ghcSrcSpanToSpan (GHC.RealSrcSpan span) = - Just (Span { spStart = Position (GHC.srcSpanStartLine span) (GHC.srcSpanStartCol span) - , spEnd = Position (GHC.srcSpanEndLine span) (GHC.srcSpanEndCol span) - }) -ghcSrcSpanToSpan _ = Nothing - enrichToken :: Token -> DetailsMap -> Maybe TokenDetails enrichToken (Token typ _ spn) dm | typ `elem` [TkIdentifier, TkOperator] = lookupBySpan spn dm @@ -99,9 +94,12 @@ variables = types :: GHC.RenamedSource -> LTokenDetails types = everythingInRenamedSource ty where + ty :: forall a. Data a => a -> [(GHC.SrcSpan, TokenDetails)] ty term = case cast term of (Just ((GHC.L sspan (GHC.HsTyVar _ _ name)) :: GHC.LHsType GHC.GhcRn)) -> pure (sspan, RtkType (GHC.unLoc name)) + (Just ((GHC.L sspan (GHC.HsOpTy _ l name r)) :: GHC.LHsType GHC.GhcRn)) -> + (sspan, RtkType (GHC.unLoc name)):(ty l ++ ty r) _ -> empty -- | Obtain details map for identifier bindings. @@ -117,6 +115,11 @@ binds = everythingInRenamedSource fun term = case cast term of (Just (GHC.FunBind _ (GHC.L sspan name) _ _ _ :: GHC.HsBind GHC.GhcRn)) -> pure (sspan, RtkBind name) + (Just (GHC.PatSynBind _ (GHC.PSB _ (GHC.L sspan name) args _ _))) -> + pure (sspan, RtkBind name) ++ everythingInRenamedSource patsyn_binds args + _ -> empty + patsyn_binds term = case cast term of + (Just (GHC.L sspan (name :: GHC.Name))) -> pure (sspan, RtkVar name) _ -> empty pat term = case cast term of (Just ((GHC.L sspan (GHC.VarPat _ name)) :: GHC.LPat GHC.GhcRn)) -> @@ -142,6 +145,7 @@ decls :: GHC.RenamedSource -> LTokenDetails decls (group, _, _, _) = concatMap ($ group) [ concat . map typ . concat . map GHC.group_tyclds . GHC.hs_tyclds , everythingInRenamedSource fun . GHC.hs_valds + , everythingInRenamedSource fix . GHC.hs_fixds , everythingInRenamedSource (con `Syb.combine` ins) ] where @@ -149,11 +153,16 @@ decls (group, _, _, _) = concatMap ($ group) GHC.DataDecl { tcdLName = name } -> pure . decl $ name GHC.SynDecl _ name _ _ _ -> pure . decl $ name GHC.FamDecl _ fam -> pure . decl $ GHC.fdLName fam - GHC.ClassDecl{..} -> [decl tcdLName] ++ concatMap sig tcdSigs + GHC.ClassDecl{..} -> + [decl tcdLName] + ++ concatMap sig tcdSigs + ++ concatMap tyfam tcdATs GHC.XTyClDecl {} -> GHC.panic "haddock:decls" fun term = case cast term of (Just (GHC.FunBind _ (GHC.L sspan name) _ _ _ :: GHC.HsBind GHC.GhcRn)) | GHC.isExternalName name -> pure (sspan, RtkDecl name) + (Just (GHC.PatSynBind _ (GHC.PSB _ (GHC.L sspan name) _ _ _))) + | GHC.isExternalName name -> pure (sspan, RtkDecl name) _ -> empty con term = case cast term of (Just (cdcl :: GHC.ConDecl GHC.GhcRn)) -> @@ -171,7 +180,17 @@ decls (group, _, _, _) = concatMap ($ group) Just (field :: GHC.ConDeclField GHC.GhcRn) -> map (decl . fmap GHC.extFieldOcc) $ GHC.cd_fld_names field Nothing -> empty + fix term = case cast term of + Just ((GHC.FixitySig _ names _) :: GHC.FixitySig GHC.GhcRn) + -> map (\(GHC.L sspan x) -> (sspan, RtkVar x)) names + Just ((GHC.XFixitySig {}) :: GHC.FixitySig GHC.GhcRn) + -> GHC.panic "haddock:decls" + Nothing -> empty + tyfam (GHC.L _ (GHC.FamilyDecl{..})) = [decl fdLName] + tyfam (GHC.L _ (GHC.XFamilyDecl {})) = GHC.panic "haddock:dels" sig (GHC.L _ (GHC.TypeSig _ names _)) = map decl names + sig (GHC.L _ (GHC.PatSynSig _ names _)) = map decl names + sig (GHC.L _ (GHC.ClassOpSig _ _ names _)) = map decl names sig _ = [] decl (GHC.L sspan name) = (sspan, RtkDecl name) tyref (GHC.L sspan name) = (sspan, RtkType name) @@ -190,10 +209,11 @@ imports src@(_, imps, _, _) = (Just (GHC.IEThingAll _ t)) -> pure $ typ $ GHC.ieLWrappedName t (Just (GHC.IEThingWith _ t _ vs _fls)) -> [typ $ GHC.ieLWrappedName t] ++ map (var . GHC.ieLWrappedName) vs + (Just (GHC.IEModuleContents _ m)) -> pure $ modu m _ -> empty typ (GHC.L sspan name) = (sspan, RtkType name) var (GHC.L sspan name) = (sspan, RtkVar name) - imp idecl | not . GHC.ideclImplicit $ idecl = - let (GHC.L sspan name) = GHC.ideclName idecl - in Just (sspan, RtkModule name) - imp _ = Nothing + modu (GHC.L sspan name) = (sspan, RtkModule name) + imp idecl + | not . GHC.ideclImplicit $ idecl = Just (modu (GHC.ideclName idecl)) + | otherwise = Nothing diff --git a/haddock-api/src/Haddock/Backends/Hyperlinker/Parser.hs b/haddock-api/src/Haddock/Backends/Hyperlinker/Parser.hs index e4345602..e7ecac73 100644 --- a/haddock-api/src/Haddock/Backends/Hyperlinker/Parser.hs +++ b/haddock-api/src/Haddock/Backends/Hyperlinker/Parser.hs @@ -1,11 +1,19 @@ module Haddock.Backends.Hyperlinker.Parser (parse) where +import Data.Either ( isRight, isLeft ) +import Data.List ( foldl', isPrefixOf, isSuffixOf ) +import Data.Maybe ( maybeToList ) +import Data.Char ( isSpace ) +import qualified Text.Read as R -import Data.Char -import Data.List -import Data.Maybe +import GHC ( DynFlags, addSourceToTokens ) +import SrcLoc +import FastString ( mkFastString ) +import StringBuffer ( stringToStringBuffer ) +import Lexer ( Token(..) ) +import qualified Lexer as L -import Haddock.Backends.Hyperlinker.Types +import Haddock.Backends.Hyperlinker.Types as T -- | Turn source code string into a stream of more descriptive tokens. @@ -13,202 +21,419 @@ import Haddock.Backends.Hyperlinker.Types -- Result should retain original file layout (including comments, whitespace, -- etc.), i.e. the following "law" should hold: -- --- @concat . map 'tkValue' . 'parse' = id@ -parse :: String -> [Token] -parse = tokenize . tag . chunk +-- prop> concat . map tkValue . parse = id +-- +-- (In reality, this only holds for input not containing '\r', '\t', '\f', '\v', +-- characters, since GHC transforms those into ' ' and '\n') +parse :: DynFlags -> FilePath -> String -> [T.Token] +parse dflags fp = ghcToks . processCPP dflags fp . filterCRLF + where + -- Remove CRLFs from source + filterCRLF :: String -> String + filterCRLF ('\r':'\n':cs) = '\n' : filterCRLF cs + filterCRLF (c:cs) = c : filterCRLF cs + filterCRLF [] = [] --- | Split raw source string to more meaningful chunks. +-- | Parse the source into tokens using the GHC lexer. -- --- This is the initial stage of tokenization process. Each chunk is either --- a comment (including comment delimiters), a whitespace string, preprocessor --- macro (and all its content until the end of a line) or valid Haskell lexeme. -chunk :: String -> [String] -chunk [] = [] -chunk str@(c:_) - | isSpace c = - let (space, mcpp, rest) = spanSpaceOrCpp str - in [space] ++ maybeToList mcpp ++ chunk rest -chunk str - | "--" `isPrefixOf` str = chunk' $ spanToNewline str - | "{-" `isPrefixOf` str = chunk' $ chunkComment 0 str - | otherwise = case lex' str of - (tok:_) -> chunk' tok - [] -> [str] +-- * CPP lines are removed and reinserted as line-comments +-- * top-level file pragmas are parsed as block comments (see the +-- 'ITblockComment' case of 'classify' for more details) +-- +processCPP :: DynFlags -- ^ GHC's flags + -> FilePath -- ^ source file name (for position information) + -> String -- ^ source file contents + -> [(Located L.Token, String)] +processCPP dflags fpath s = addSrc . go start . splitCPP $ s where - chunk' (c, rest) = c:(chunk rest) + start = mkRealSrcLoc (mkFastString fpath) 1 1 + addSrc = addSourceToTokens start (stringToStringBuffer s) --- | A bit better lexer then the default, i.e. handles DataKinds quotes -lex' :: ReadS String -lex' ('\'' : '\'' : rest) = [("''", rest)] -lex' str@('\'' : '\\' : _ : '\'' : _) = lex str -lex' str@('\'' : _ : '\'' : _) = lex str -lex' ('\'' : rest) = [("'", rest)] -lex' str = lex str + -- Transform a list of Haskell/CPP lines into a list of tokens + go :: RealSrcLoc -> [Either String String] -> [Located L.Token] + go _ [] = [] + go pos ls = + let (hLinesRight, ls') = span isRight ls + (cppLinesLeft, rest) = span isLeft ls' --- | Split input to "first line" string and the rest of it. --- --- Ideally, this should be done simply with @'break' (== '\n')@. However, --- Haskell also allows line-unbreaking (or whatever it is called) so things --- are not as simple and this function deals with that. -spanToNewline :: String -> (String, String) -spanToNewline [] = ([], []) -spanToNewline ('\\':'\n':str) = - let (str', rest) = spanToNewline str - in ('\\':'\n':str', rest) -spanToNewline str@('\n':_) = ("", str) -spanToNewline (c:str) = - let (str', rest) = spanToNewline str - in (c:str', rest) + hSrc = concat [ hLine | Right hLine <- hLinesRight ] + cppSrc = concat [ cppLine | Left cppLine <- cppLinesLeft ] + + in case L.lexTokenStream (stringToStringBuffer hSrc) pos dflags of --- | Split input to whitespace string, (optional) preprocessor directive and --- the rest of it. + -- Stuff that fails to lex gets turned into comments + L.PFailed _ _ss _msg -> + let (src_pos, failed) = mkToken ITunknown pos hSrc + (new_pos, cpp) = mkToken ITlineComment src_pos cppSrc + in failed : cpp : go new_pos rest + + -- Successfully lexed + L.POk ss toks -> + let (new_pos, cpp) = mkToken ITlineComment (L.loc ss) cppSrc + in toks ++ [cpp] ++ go new_pos rest + + -- Manually make a token from a 'String', advancing the cursor position + mkToken tok start' str = + let end = foldl' advanceSrcLoc start' str + in (end, L (RealSrcSpan $ mkRealSrcSpan start' end) (tok str)) + + +-- | Split apart the initial file into Haskell source lines ('Left' entries) and +-- CPP lines ('Right' entries). -- --- Again, using something like @'span' 'isSpace'@ would be nice to chunk input --- to whitespace. The problem is with /#/ symbol - if it is placed at the very --- beginning of a line, it should be recognized as preprocessor macro. In any --- other case, it is ordinary Haskell symbol and can be used to declare --- operators. Hence, while dealing with whitespace we also check whether there --- happens to be /#/ symbol just after a newline character - if that is the --- case, we begin treating the whole line as preprocessor macro. -spanSpaceOrCpp :: String -> (String, Maybe String, String) -spanSpaceOrCpp ('\n':'#':str) = - let (str', rest) = spanToNewline str - in ("\n", Just $ '#':str', rest) -spanSpaceOrCpp (c:str') - | isSpace c = - let (space, mcpp, rest) = spanSpaceOrCpp str' - in (c:space, mcpp, rest) -spanSpaceOrCpp str = ("", Nothing, str) - --- | Split input to comment content (including delimiters) and the rest. +-- All characters in the input are present in the output: -- --- Again, some more logic than simple 'span' is required because of Haskell --- comment nesting policy. -chunkComment :: Int -> String -> (String, String) -chunkComment _ [] = ("", "") -chunkComment depth ('{':'-':str) = - let (c, rest) = chunkComment (depth + 1) str - in ("{-" ++ c, rest) -chunkComment depth ('-':'}':str) - | depth == 1 = ("-}", str) - | otherwise = - let (c, rest) = chunkComment (depth - 1) str - in ("-}" ++ c, rest) -chunkComment depth (e:str) = - let (c, rest) = chunkComment depth str - in (e:c, rest) - --- | Assign source location for each chunk in given stream. -tag :: [String] -> [(Span, String)] -tag = - reverse . snd . foldl aux (Position 1 1, []) +-- prop> concat . map (either id id) . splitCPP = id +splitCPP :: String -> [Either String String] +splitCPP "" = [] +splitCPP s | isCPPline s = Left l : splitCPP rest + | otherwise = Right l : splitCPP rest where - aux (pos, cs) str = - let pos' = foldl move pos str - in (pos', (Span pos pos', str):cs) - move pos '\n' = pos { posRow = posRow pos + 1, posCol = 1 } - move pos _ = pos { posCol = posCol pos + 1 } - --- | Turn unrecognised chunk stream to more descriptive token stream. -tokenize :: [(Span, String)] -> [Token] -tokenize = - map aux - where - aux (sp, str) = Token - { tkType = classify str - , tkValue = str - , tkSpan = sp - } + ~(l, rest) = spanToNewline 0 s + --- | Classify given string as appropriate Haskell token. +-- | Heuristic to decide if a line is going to be a CPP line. This should be a +-- cheap operation since it is going to be run on every line being processed. +-- +-- Right now it just checks if the first non-whitespace character in the first +-- five characters of the line is a '#': -- --- This method is based on Haskell 98 Report lexical structure description: --- https://www.haskell.org/onlinereport/lexemes.html +-- >>> isCPPline "#define FOO 1" +-- True -- --- However, this is probably far from being perfect and most probably does not --- handle correctly all corner cases. -classify :: String -> TokenType -classify str - | "--" `isPrefixOf` str = TkComment - | "{-#" `isPrefixOf` str = TkPragma - | "{-" `isPrefixOf` str = TkComment -classify "''" = TkSpecial -classify "'" = TkSpecial -classify str@(c:_) - | isSpace c = TkSpace - | isDigit c = TkNumber - | c `elem` special = TkSpecial - | str `elem` glyphs = TkGlyph - | all (`elem` symbols) str = TkOperator - | c == '#' = TkCpp - | c == '"' = TkString - | c == '\'' = TkChar -classify str - | str `elem` keywords = TkKeyword - | isIdentifier str = TkIdentifier - | otherwise = TkUnknown - -keywords :: [String] -keywords = - [ "as" - , "case" - , "class" - , "data" - , "default" - , "deriving" - , "do" - , "else" - , "hiding" - , "if" - , "import" - , "in" - , "infix" - , "infixl" - , "infixr" - , "instance" - , "let" - , "module" - , "newtype" - , "of" - , "qualified" - , "then" - , "type" - , "where" - , "forall" - , "family" - , "mdo" - ] - -glyphs :: [String] -glyphs = - [ ".." - , ":" - , "::" - , "=" - , "\\" - , "|" - , "<-" - , "->" - , "@" - , "~" - , "~#" - , "=>" - , "-" - , "!" - ] - -special :: [Char] -special = "()[]{},;`" - --- TODO: Add support for any Unicode symbol or punctuation. --- source: http://stackoverflow.com/questions/10548170/what-characters-are-permitted-for-haskell-operators -symbols :: [Char] -symbols = "!#$%&*+./<=>?@\\^|-~:" - -isIdentifier :: String -> Bool -isIdentifier (s:str) - | (isLower' s || isUpper s) && all isAlphaNum' str = True +-- >>> isCPPline "\t\t #ifdef GHC" +-- True +-- +-- >>> isCPPline " #endif" +-- False +-- +isCPPline :: String -> Bool +isCPPline = isPrefixOf "#" . dropWhile (`elem` " \t") . take 5 + + +-- | Split a "line" off the front of a string, hopefully without cutting tokens +-- in half. I say "hopefully" because knowing what a token is requires lexing, +-- yet lexing depends on this function. +-- +-- All characters in the input are present in the output: +-- +-- prop> curry (++) . spanToNewLine 0 = id +spanToNewline :: Int -- ^ open '{-' + -> String -- ^ input + -> (String, String) + +-- Base case and space characters +spanToNewline _ "" = ("", "") +spanToNewline n ('\n':str) | n <= 0 = ("\n", str) +spanToNewline n ('\n':str) | n <= 0 = ("\n", str) +spanToNewline n ('\\':'\n':str) = + let (str', rest) = spanToNewline n str + in ('\\':'\n':str', rest) + +-- Block comments +spanToNewline n ('{':'-':str) = + let (str', rest) = spanToNewline (n+1) str + in ('{':'-':str', rest) +spanToNewline n ('-':'}':str) = + let (str', rest) = spanToNewline (n-1) str + in ('-':'}':str', rest) + +-- When not in a block comment, try to lex a Haskell token +spanToNewline 0 str@(c:_) | ((lexed, str') : _) <- R.lex str, not (isSpace c) = + if all (== '-') lexed && length lexed >= 2 + -- A Haskell line comment + then case span (/= '\n') str' of + (str'', '\n':rest) -> (lexed ++ str'' ++ "\n", rest) + (_, _) -> (str, "") + + -- An actual Haskell token + else let (str'', rest) = spanToNewline 0 str' + in (lexed ++ str'', rest) + +-- In all other cases, advance one character at a time +spanToNewline n (c:str) = + let (str', rest) = spanToNewline n str + in (c:str', rest) + + +-- | Turn a list of GHC's 'L.Token' (and their source 'String') into a list of +-- Haddock's 'T.Token'. +ghcToks :: [(Located L.Token, String)] -> [T.Token] +ghcToks = reverse . (\(_,ts,_) -> ts) . foldl' go (start, [], False) where - isLower' c = isLower c || c == '_' - isAlphaNum' c = isAlphaNum c || c == '_' || c == '\'' -isIdentifier _ = False + start = mkRealSrcLoc (mkFastString "lexing") 1 1 + + go :: (RealSrcLoc, [T.Token], Bool) + -- ^ current position, tokens accumulated, currently in pragma (or not) + + -> (Located L.Token, String) + -- ^ next token, its content + + -> (RealSrcLoc, [T.Token], Bool) + -- ^ new position, new tokens accumulated, currently in pragma (or not) + + go (pos, toks, in_prag) (L l tok, raw) = + ( next_pos + , classifiedTok ++ maybeToList white ++ toks + , inPragma in_prag tok + ) + where + (next_pos, white) = mkWhitespace pos l + + classifiedTok = [ Token (classify' tok) raw rss + | RealSrcSpan rss <- [l] + , not (null raw) + ] + + classify' | in_prag = const TkPragma + | otherwise = classify + + +-- | Find the correct amount of whitespace between tokens. +mkWhitespace :: RealSrcLoc -> SrcSpan -> (RealSrcLoc, Maybe T.Token) +mkWhitespace prev spn = + case spn of + UnhelpfulSpan _ -> (prev,Nothing) + RealSrcSpan s | null wsstring -> (end, Nothing) + | otherwise -> (end, Just (Token TkSpace wsstring wsspan)) + where + start = realSrcSpanStart s + end = realSrcSpanEnd s + wsspan = mkRealSrcSpan prev start + nls = srcLocLine start - srcLocLine prev + spaces = if nls == 0 then srcLocCol start - srcLocCol prev + else srcLocCol start - 1 + wsstring = replicate nls '\n' ++ replicate spaces ' ' + + +-- | Classify given tokens as appropriate Haskell token type. +classify :: L.Token -> TokenType +classify tok = + case tok of + ITas -> TkKeyword + ITcase -> TkKeyword + ITclass -> TkKeyword + ITdata -> TkKeyword + ITdefault -> TkKeyword + ITderiving -> TkKeyword + ITdo -> TkKeyword + ITelse -> TkKeyword + IThiding -> TkKeyword + ITforeign -> TkKeyword + ITif -> TkKeyword + ITimport -> TkKeyword + ITin -> TkKeyword + ITinfix -> TkKeyword + ITinfixl -> TkKeyword + ITinfixr -> TkKeyword + ITinstance -> TkKeyword + ITlet -> TkKeyword + ITmodule -> TkKeyword + ITnewtype -> TkKeyword + ITof -> TkKeyword + ITqualified -> TkKeyword + ITthen -> TkKeyword + ITtype -> TkKeyword + ITvia -> TkKeyword + ITwhere -> TkKeyword + + ITforall {} -> TkKeyword + ITexport -> TkKeyword + ITlabel -> TkKeyword + ITdynamic -> TkKeyword + ITsafe -> TkKeyword + ITinterruptible -> TkKeyword + ITunsafe -> TkKeyword + ITstdcallconv -> TkKeyword + ITccallconv -> TkKeyword + ITcapiconv -> TkKeyword + ITprimcallconv -> TkKeyword + ITjavascriptcallconv -> TkKeyword + ITmdo -> TkKeyword + ITfamily -> TkKeyword + ITrole -> TkKeyword + ITgroup -> TkKeyword + ITby -> TkKeyword + ITusing -> TkKeyword + ITpattern -> TkKeyword + ITstatic -> TkKeyword + ITstock -> TkKeyword + ITanyclass -> TkKeyword + + ITunit -> TkKeyword + ITsignature -> TkKeyword + ITdependency -> TkKeyword + ITrequires -> TkKeyword + + ITinline_prag {} -> TkPragma + ITspec_prag {} -> TkPragma + ITspec_inline_prag {} -> TkPragma + ITsource_prag {} -> TkPragma + ITrules_prag {} -> TkPragma + ITwarning_prag {} -> TkPragma + ITdeprecated_prag {} -> TkPragma + ITline_prag {} -> TkPragma + ITcolumn_prag {} -> TkPragma + ITscc_prag {} -> TkPragma + ITgenerated_prag {} -> TkPragma + ITcore_prag {} -> TkPragma + ITunpack_prag {} -> TkPragma + ITnounpack_prag {} -> TkPragma + ITann_prag {} -> TkPragma + ITcomplete_prag {} -> TkPragma + ITclose_prag -> TkPragma + IToptions_prag {} -> TkPragma + ITinclude_prag {} -> TkPragma + ITlanguage_prag -> TkPragma + ITminimal_prag {} -> TkPragma + IToverlappable_prag {} -> TkPragma + IToverlapping_prag {} -> TkPragma + IToverlaps_prag {} -> TkPragma + ITincoherent_prag {} -> TkPragma + ITctype {} -> TkPragma + + ITdotdot -> TkGlyph + ITcolon -> TkGlyph + ITdcolon {} -> TkGlyph + ITequal -> TkGlyph + ITlam -> TkGlyph + ITlcase -> TkGlyph + ITvbar -> TkGlyph + ITlarrow {} -> TkGlyph + ITrarrow {} -> TkGlyph + ITat -> TkGlyph + ITtilde -> TkGlyph + ITdarrow {} -> TkGlyph + ITminus -> TkGlyph + ITbang -> TkGlyph + ITdot -> TkOperator + ITtypeApp -> TkGlyph + + ITbiglam -> TkGlyph + + ITocurly -> TkSpecial + ITccurly -> TkSpecial + ITvocurly -> TkSpecial + ITvccurly -> TkSpecial + ITobrack -> TkSpecial + ITopabrack -> TkSpecial + ITcpabrack -> TkSpecial + ITcbrack -> TkSpecial + IToparen -> TkSpecial + ITcparen -> TkSpecial + IToubxparen -> TkSpecial + ITcubxparen -> TkSpecial + ITsemi -> TkSpecial + ITcomma -> TkSpecial + ITunderscore -> TkIdentifier + ITbackquote -> TkSpecial + ITsimpleQuote -> TkSpecial + + ITvarid {} -> TkIdentifier + ITconid {} -> TkIdentifier + ITvarsym {} -> TkOperator + ITconsym {} -> TkOperator + ITqvarid {} -> TkIdentifier + ITqconid {} -> TkIdentifier + ITqvarsym {} -> TkOperator + ITqconsym {} -> TkOperator + + ITdupipvarid {} -> TkUnknown + ITlabelvarid {} -> TkUnknown + + ITchar {} -> TkChar + ITstring {} -> TkString + ITinteger {} -> TkNumber + ITrational {} -> TkNumber + + ITprimchar {} -> TkChar + ITprimstring {} -> TkString + ITprimint {} -> TkNumber + ITprimword {} -> TkNumber + ITprimfloat {} -> TkNumber + ITprimdouble {} -> TkNumber + + ITopenExpQuote {} -> TkSpecial + ITopenPatQuote -> TkSpecial + ITopenDecQuote -> TkSpecial + ITopenTypQuote -> TkSpecial + ITcloseQuote {} -> TkSpecial + ITopenTExpQuote {} -> TkSpecial + ITcloseTExpQuote -> TkSpecial + ITidEscape {} -> TkUnknown + ITparenEscape -> TkSpecial + ITidTyEscape {} -> TkUnknown + ITparenTyEscape -> TkSpecial + ITtyQuote -> TkSpecial + ITquasiQuote {} -> TkUnknown + ITqQuasiQuote {} -> TkUnknown + + ITproc -> TkKeyword + ITrec -> TkKeyword + IToparenbar {} -> TkGlyph + ITcparenbar {} -> TkGlyph + ITlarrowtail {} -> TkGlyph + ITrarrowtail {} -> TkGlyph + ITLarrowtail {} -> TkGlyph + ITRarrowtail {} -> TkGlyph + + ITunknown {} -> TkUnknown + ITeof -> TkUnknown + + -- Line comments are only supposed to start with '--'. Starting with '#' + -- means that this was probably a CPP. + ITlineComment s + | isCPPline s -> TkCpp + | otherwise -> TkComment + + ITdocCommentNext {} -> TkComment + ITdocCommentPrev {} -> TkComment + ITdocCommentNamed {} -> TkComment + ITdocSection {} -> TkComment + ITdocOptions {} -> TkComment + + -- The lexer considers top-level pragmas as comments (see `pragState` in + -- the GHC lexer for more), so we have to manually reverse this. The + -- following is a hammer: it smashes _all_ pragma-like block comments into + -- pragmas. + ITblockComment c + | isPrefixOf "{-#" c + , isSuffixOf "#-}" c -> TkPragma + | otherwise -> TkComment + +-- | Classify given tokens as beginning pragmas (or not). +inPragma :: Bool -- ^ currently in pragma + -> L.Token -- ^ current token + -> Bool -- ^ new information about whether we are in a pragma +inPragma _ ITclose_prag = False +inPragma True _ = True +inPragma False tok = + case tok of + ITinline_prag {} -> True + ITspec_prag {} -> True + ITspec_inline_prag {} -> True + ITsource_prag {} -> True + ITrules_prag {} -> True + ITwarning_prag {} -> True + ITdeprecated_prag {} -> True + ITline_prag {} -> True + ITcolumn_prag {} -> True + ITscc_prag {} -> True + ITgenerated_prag {} -> True + ITcore_prag {} -> True + ITunpack_prag {} -> True + ITnounpack_prag {} -> True + ITann_prag {} -> True + ITcomplete_prag {} -> True + IToptions_prag {} -> True + ITinclude_prag {} -> True + ITlanguage_prag -> True + ITminimal_prag {} -> True + IToverlappable_prag {} -> True + IToverlapping_prag {} -> True + IToverlaps_prag {} -> True + ITincoherent_prag {} -> True + ITctype {} -> True + + _ -> False + diff --git a/haddock-api/src/Haddock/Backends/Hyperlinker/Renderer.hs b/haddock-api/src/Haddock/Backends/Hyperlinker/Renderer.hs index 15793f0c..d7ea70a6 100644 --- a/haddock-api/src/Haddock/Backends/Hyperlinker/Renderer.hs +++ b/haddock-api/src/Haddock/Backends/Hyperlinker/Renderer.hs @@ -1,6 +1,5 @@ {-# LANGUAGE RecordWildCards #-} - module Haddock.Backends.Hyperlinker.Renderer (render) where @@ -15,7 +14,6 @@ import System.FilePath.Posix ((</>)) import Data.List import Data.Maybe -import Data.Monoid import qualified Data.Map as Map import Text.XHtml (Html, HtmlAttr, (!)) @@ -29,36 +27,10 @@ render :: Maybe FilePath -> Maybe FilePath -> SrcMap -> [RichToken] -> Html render mcss mjs srcs tokens = header mcss mjs <> body srcs tokens - -data TokenGroup - = GrpNormal Token - | GrpRich TokenDetails [Token] - - --- | Group consecutive tokens pointing to the same element. --- --- We want to render qualified identifiers as one entity. For example, --- @Bar.Baz.foo@ consists of 5 tokens (@Bar@, @.@, @Baz@, @.@, @foo@) but for --- better user experience when highlighting and clicking links, these tokens --- should be regarded as one identifier. Therefore, before rendering we must --- group consecutive elements pointing to the same 'GHC.Name' (note that even --- dot token has it if it is part of qualified name). -groupTokens :: [RichToken] -> [TokenGroup] -groupTokens [] = [] -groupTokens ((RichToken tok Nothing):rest) = (GrpNormal tok):(groupTokens rest) -groupTokens ((RichToken tok (Just det)):rest) = - let (grp, rest') = span same rest - in (GrpRich det (tok:(map rtkToken grp))):(groupTokens rest') - where - same (RichToken _ (Just det')) = det == det' - same _ = False - - body :: SrcMap -> [RichToken] -> Html -body srcs tokens = - Html.body . Html.pre $ hypsrc +body srcs tokens = Html.body . Html.pre $ hypsrc where - hypsrc = mconcat . map (tokenGroup srcs) . groupTokens $ tokens + hypsrc = mconcat . map (richToken srcs) $ tokens header :: Maybe FilePath -> Maybe FilePath -> Html @@ -79,29 +51,20 @@ header mcss mjs = , Html.src scriptFile ] - -tokenGroup :: SrcMap -> TokenGroup -> Html -tokenGroup _ (GrpNormal tok@(Token { .. })) - | tkType == TkSpace = renderSpace (posRow . spStart $ tkSpan) tkValue - | otherwise = tokenSpan tok ! attrs +-- | Given information about the source position of definitions, render a token +richToken :: SrcMap -> RichToken -> Html +richToken srcs (RichToken Token{..} details) + | tkType == TkSpace = renderSpace (GHC.srcSpanStartLine tkSpan) tkValue + | otherwise = linked content where - attrs = [ multiclass . tokenStyle $ tkType ] -tokenGroup srcs (GrpRich det tokens) = - externalAnchor det . internalAnchor det . hyperlink srcs det $ content - where - content = mconcat . map (richToken det) $ tokens - - -richToken :: TokenDetails -> Token -> Html -richToken det tok = - tokenSpan tok ! [ multiclass style ] - where - style = (tokenStyle . tkType) tok ++ richTokenStyle det - - -tokenSpan :: Token -> Html -tokenSpan = Html.thespan . Html.toHtml . tkValue + content = tokenSpan ! [ multiclass style ] + tokenSpan = Html.thespan (Html.toHtml tkValue) + style = tokenStyle tkType ++ maybe [] richTokenStyle details + -- If we have name information, we can make links + linked = case details of + Just d -> externalAnchor d . internalAnchor d . hyperlink srcs d + Nothing -> id richTokenStyle :: TokenDetails -> [StyleClass] richTokenStyle (RtkVar _) = ["hs-var"] @@ -155,7 +118,7 @@ internalHyperlink name content = Html.anchor content ! [ Html.href $ "#" ++ internalAnchorIdent name ] externalNameHyperlink :: SrcMap -> GHC.Name -> Html -> Html -externalNameHyperlink (srcs, _) name content = case Map.lookup mdl srcs of +externalNameHyperlink srcs name content = case Map.lookup mdl srcs of Just SrcLocal -> Html.anchor content ! [ Html.href $ hypSrcModuleNameUrl mdl name ] Just (SrcExternal path) -> Html.anchor content ! @@ -165,12 +128,14 @@ externalNameHyperlink (srcs, _) name content = case Map.lookup mdl srcs of mdl = GHC.nameModule name externalModHyperlink :: SrcMap -> GHC.ModuleName -> Html -> Html -externalModHyperlink (_, srcs) name content = case Map.lookup name srcs of - Just SrcLocal -> Html.anchor content ! +externalModHyperlink srcs name content = + let srcs' = Map.mapKeys GHC.moduleName srcs in + case Map.lookup name srcs' of + Just SrcLocal -> Html.anchor content ! [ Html.href $ hypSrcModuleUrl' name ] - Just (SrcExternal path) -> Html.anchor content ! + Just (SrcExternal path) -> Html.anchor content ! [ Html.href $ path </> hypSrcModuleUrl' name ] - Nothing -> content + Nothing -> content renderSpace :: Int -> String -> Html diff --git a/haddock-api/src/Haddock/Backends/Hyperlinker/Types.hs b/haddock-api/src/Haddock/Backends/Hyperlinker/Types.hs index d8ae89e4..e377471e 100644 --- a/haddock-api/src/Haddock/Backends/Hyperlinker/Types.hs +++ b/haddock-api/src/Haddock/Backends/Hyperlinker/Types.hs @@ -4,8 +4,6 @@ module Haddock.Backends.Hyperlinker.Types where import qualified GHC import Data.Map (Map) -import qualified Data.Map as Map - data Token = Token { tkType :: TokenType @@ -14,23 +12,8 @@ data Token = Token } deriving (Show) -data Position = Position - { posRow :: !Int - , posCol :: !Int - } - deriving (Eq, Ord, Show) - -data Span = Span - { spStart :: !Position - , spEnd :: !Position - } - deriving (Show) - --- | Tests whether the first span "contains" the other span, meaning --- that it covers at least as much source code. True where spans are equal. -containsSpan :: Span -> Span -> Bool -containsSpan s1 s2 = - spStart s1 <= spStart s2 && spEnd s1 >= spEnd s2 +type Position = GHC.RealSrcLoc +type Span = GHC.RealSrcSpan data TokenType = TkIdentifier @@ -80,15 +63,5 @@ data SrcPath | SrcLocal -- | Mapping from modules to cross-package source paths. --- --- This mapping is actually a pair of maps instead of just one map. The reason --- for this is because when hyperlinking modules in import lists we have no --- 'GHC.Module' available. On the other hand, we can't just use map with --- 'GHC.ModuleName' as indices because certain modules may have common name --- but originate in different packages. Hence, we use both /rich/ and /poor/ --- versions, where the /poor/ is just projection of /rich/ one cached in pair --- for better performance. -type SrcMap = (Map GHC.Module SrcPath, Map GHC.ModuleName SrcPath) +type SrcMap = Map GHC.Module SrcPath -mkSrcMap :: Map GHC.Module SrcPath -> SrcMap -mkSrcMap srcs = (srcs, Map.mapKeys GHC.moduleName srcs) diff --git a/haddock-api/src/Haddock/Backends/LaTeX.hs b/haddock-api/src/Haddock/Backends/LaTeX.hs index 597f1f15..3cc4c278 100644 --- a/haddock-api/src/Haddock/Backends/LaTeX.hs +++ b/haddock-api/src/Haddock/Backends/LaTeX.hs @@ -27,7 +27,7 @@ import GHC import OccName import Name ( nameOccName ) import RdrName ( rdrNameOcc ) -import FastString ( unpackFS, unpackLitString, zString ) +import FastString ( unpackFS ) import Outputable ( panic) import qualified Data.Map as Map @@ -539,13 +539,11 @@ ppClassDecl instances doc subdocs methodTable = text "\\haddockpremethods{}\\textbf{Methods}" $$ - vcat [ ppFunSig doc names (hsSigWcType typ) unicode + vcat [ ppFunSig doc [name] (hsSigWcType typ) unicode | L _ (TypeSig _ lnames typ) <- lsigs - , let doc = lookupAnySubdoc (head names) subdocs - names = map unLoc lnames ] - -- FIXME: is taking just the first name ok? Is it possible that - -- there are different subdocs for different names in a single - -- type signature? + , name <- map unLoc lnames + , let doc = lookupAnySubdoc name subdocs + ] instancesBit = ppDocInstances unicode instances @@ -563,14 +561,14 @@ ppDocInstances unicode (i : rest) (is, rest') = spanWith isUndocdInstance rest isUndocdInstance :: DocInstance a -> Maybe (InstHead a) -isUndocdInstance (i,Nothing,_) = Just i +isUndocdInstance (i,Nothing,_,_) = Just i isUndocdInstance _ = Nothing -- | Print a possibly commented instance. The instance header is printed inside -- an 'argBox'. The comment is printed to the right of the box in normal comment -- style. ppDocInstance :: Bool -> DocInstance DocNameI -> LaTeX -ppDocInstance unicode (instHead, doc, _) = +ppDocInstance unicode (instHead, doc, _, _) = declWithDoc (ppInstDecl unicode instHead) (fmap docToLaTeX $ fmap _doc doc) @@ -1139,7 +1137,8 @@ parLatexMarkup ppId = Markup { markupAName = \_ _ -> empty, markupProperty = \p _ -> quote $ verb $ text p, markupExample = \e _ -> quote $ verb $ text $ unlines $ map exampleToString e, - markupHeader = \(Header l h) p -> header l (h p) + markupHeader = \(Header l h) p -> header l (h p), + markupTable = \(Table h b) p -> table h b p } where header 1 d = text "\\section*" <> braces d @@ -1148,6 +1147,8 @@ parLatexMarkup ppId = Markup { | l > 0 && l <= 6 = text "\\subsubsection*" <> braces d header l _ = error $ "impossible header level in LaTeX generation: " ++ show l + table _ _ _ = text "{TODO: Table}" + fixString Plain s = latexFilter s fixString Verb s = s fixString Mono s = latexMonoFilter s diff --git a/haddock-api/src/Haddock/Backends/Xhtml.hs b/haddock-api/src/Haddock/Backends/Xhtml.hs index 464c166b..6da6a2e8 100644 --- a/haddock-api/src/Haddock/Backends/Xhtml.hs +++ b/haddock-api/src/Haddock/Backends/Xhtml.hs @@ -70,6 +70,7 @@ ppHtml :: DynFlags -> Maybe String -- ^ The contents URL (--use-contents) -> Maybe String -- ^ The index URL (--use-index) -> Bool -- ^ Whether to use unicode in output (--use-unicode) + -> Maybe String -- ^ Package name -> QualOption -- ^ How to qualify names -> Bool -- ^ Output pretty html (newlines and indenting) -> Bool -- ^ Also write Quickjump index @@ -78,7 +79,7 @@ ppHtml :: DynFlags ppHtml dflags doctitle maybe_package ifaces reexported_ifaces odir prologue themes maybe_mathjax_url maybe_source_url maybe_wiki_url maybe_contents_url maybe_index_url unicode - qual debug withQuickjump = do + pkg qual debug withQuickjump = do let visible_ifaces = filter visible ifaces visible i = OptHide `notElem` ifaceOptions i @@ -88,7 +89,7 @@ ppHtml dflags doctitle maybe_package ifaces reexported_ifaces odir prologue themes maybe_mathjax_url maybe_index_url maybe_source_url maybe_wiki_url (map toInstalledIface visible_ifaces ++ reexported_ifaces) False -- we don't want to display the packages in a single-package contents - prologue debug (makeContentsQual qual) + prologue debug pkg (makeContentsQual qual) when (isNothing maybe_index_url) $ do ppHtmlIndex odir doctitle maybe_package @@ -96,12 +97,12 @@ ppHtml dflags doctitle maybe_package ifaces reexported_ifaces odir prologue (map toInstalledIface visible_ifaces ++ reexported_ifaces) debug when withQuickjump $ - ppJsonIndex odir maybe_source_url maybe_wiki_url unicode qual + ppJsonIndex odir maybe_source_url maybe_wiki_url unicode pkg qual visible_ifaces mapM_ (ppHtmlModule odir doctitle themes maybe_mathjax_url maybe_source_url maybe_wiki_url - maybe_contents_url maybe_index_url unicode qual debug) visible_ifaces + maybe_contents_url maybe_index_url unicode pkg qual debug) visible_ifaces copyHtmlBits :: FilePath -> FilePath -> Themes -> Bool -> IO () @@ -258,11 +259,12 @@ ppHtmlContents -> WikiURLs -> [InstalledInterface] -> Bool -> Maybe (MDoc GHC.RdrName) -> Bool + -> Maybe Package -- ^ Current package -> Qualification -- ^ How to qualify names -> IO () ppHtmlContents dflags odir doctitle _maybe_package themes mathjax_url maybe_index_url - maybe_source_url maybe_wiki_url ifaces showPkgs prologue debug qual = do + maybe_source_url maybe_wiki_url ifaces showPkgs prologue debug pkg qual = do let tree = mkModuleTree dflags showPkgs [(instMod iface, toInstalledDescription iface) | iface <- ifaces @@ -276,41 +278,41 @@ ppHtmlContents dflags odir doctitle _maybe_package bodyHtml doctitle Nothing maybe_source_url maybe_wiki_url Nothing maybe_index_url << [ - ppPrologue qual doctitle prologue, - ppSignatureTree qual sig_tree, - ppModuleTree qual tree + ppPrologue pkg qual doctitle prologue, + ppSignatureTree pkg qual sig_tree, + ppModuleTree pkg qual tree ] createDirectoryIfMissing True odir writeFile (joinPath [odir, contentsHtmlFile]) (renderToString debug html) -ppPrologue :: Qualification -> String -> Maybe (MDoc GHC.RdrName) -> Html -ppPrologue _ _ Nothing = noHtml -ppPrologue qual title (Just doc) = - divDescription << (h1 << title +++ docElement thediv (rdrDocToHtml qual doc)) +ppPrologue :: Maybe Package -> Qualification -> String -> Maybe (MDoc GHC.RdrName) -> Html +ppPrologue _ _ _ Nothing = noHtml +ppPrologue pkg qual title (Just doc) = + divDescription << (h1 << title +++ docElement thediv (rdrDocToHtml pkg qual doc)) -ppSignatureTree :: Qualification -> [ModuleTree] -> Html -ppSignatureTree qual ts = - divModuleList << (sectionName << "Signatures" +++ mkNodeList qual [] "n" ts) +ppSignatureTree :: Maybe Package -> Qualification -> [ModuleTree] -> Html +ppSignatureTree pkg qual ts = + divModuleList << (sectionName << "Signatures" +++ mkNodeList pkg qual [] "n" ts) -ppModuleTree :: Qualification -> [ModuleTree] -> Html -ppModuleTree _ [] = mempty -ppModuleTree qual ts = - divModuleList << (sectionName << "Modules" +++ mkNodeList qual [] "n" ts) +ppModuleTree :: Maybe Package -> Qualification -> [ModuleTree] -> Html +ppModuleTree _ _ [] = mempty +ppModuleTree pkg qual ts = + divModuleList << (sectionName << "Modules" +++ mkNodeList pkg qual [] "n" ts) -mkNodeList :: Qualification -> [String] -> String -> [ModuleTree] -> Html -mkNodeList qual ss p ts = case ts of +mkNodeList :: Maybe Package -> Qualification -> [String] -> String -> [ModuleTree] -> Html +mkNodeList pkg qual ss p ts = case ts of [] -> noHtml - _ -> unordList (zipWith (mkNode qual ss) ps ts) + _ -> unordList (zipWith (mkNode pkg qual ss) ps ts) where ps = [ p ++ '.' : show i | i <- [(1::Int)..]] -mkNode :: Qualification -> [String] -> String -> ModuleTree -> Html -mkNode qual ss p (Node s leaf _pkg srcPkg short ts) = +mkNode :: Maybe Package -> Qualification -> [String] -> String -> ModuleTree -> Html +mkNode pkg qual ss p (Node s leaf _pkg srcPkg short ts) = htmlModule <+> shortDescr +++ htmlPkg +++ subtree where modAttrs = case (ts, leaf) of @@ -330,14 +332,14 @@ mkNode qual ss p (Node s leaf _pkg srcPkg short ts) = Nothing -> toHtml s ) - shortDescr = maybe noHtml (origDocToHtml qual) short + shortDescr = maybe noHtml (origDocToHtml pkg qual) short htmlPkg = maybe noHtml (thespan ! [theclass "package"] <<) srcPkg subtree = if null ts then noHtml else collapseDetails p DetailsOpen ( thesummary ! [ theclass "hide-when-js-enabled" ] << "Submodules" +++ - mkNodeList qual (s:ss) p ts + mkNodeList pkg qual (s:ss) p ts ) @@ -350,10 +352,11 @@ ppJsonIndex :: FilePath -> SourceURLs -- ^ The source URL (--source) -> WikiURLs -- ^ The wiki URL (--wiki) -> Bool + -> Maybe Package -> QualOption -> [Interface] -> IO () -ppJsonIndex odir maybe_source_url maybe_wiki_url unicode qual_opt ifaces = do +ppJsonIndex odir maybe_source_url maybe_wiki_url unicode pkg qual_opt ifaces = do createDirectoryIfMissing True odir IO.withBinaryFile (joinPath [odir, indexJsonFile]) IO.WriteMode $ \h -> do Builder.hPutBuilder h (encodeToBuilder modules) @@ -371,7 +374,7 @@ ppJsonIndex odir maybe_source_url maybe_wiki_url unicode qual_opt ifaces = do goExport :: Module -> Qualification -> ExportItem DocNameI -> [Value] goExport mdl qual item - | Just item_html <- processExport True links_info unicode qual item + | Just item_html <- processExport True links_info unicode pkg qual item = [ Object [ "display_html" .= String (showHtmlFragment item_html) , "name" .= String (intercalate " " (map nameString names)) @@ -529,11 +532,11 @@ ppHtmlIndex odir doctitle _maybe_package themes ppHtmlModule :: FilePath -> String -> Themes -> Maybe String -> SourceURLs -> WikiURLs - -> Maybe String -> Maybe String -> Bool -> QualOption + -> Maybe String -> Maybe String -> Bool -> Maybe Package -> QualOption -> Bool -> Interface -> IO () ppHtmlModule odir doctitle themes maybe_mathjax_url maybe_source_url maybe_wiki_url - maybe_contents_url maybe_index_url unicode qual debug iface = do + maybe_contents_url maybe_index_url unicode pkg qual debug iface = do let mdl = ifaceMod iface aliases = ifaceModuleAliases iface @@ -555,7 +558,7 @@ ppHtmlModule odir doctitle themes maybe_source_url maybe_wiki_url maybe_contents_url maybe_index_url << [ divModuleHeader << (moduleInfo iface +++ (sectionName << mdl_str_linked)), - ifaceToHtml maybe_source_url maybe_wiki_url iface unicode real_qual + ifaceToHtml maybe_source_url maybe_wiki_url iface unicode pkg real_qual ] createDirectoryIfMissing True odir @@ -565,9 +568,9 @@ signatureDocURL :: String signatureDocURL = "https://wiki.haskell.org/Module_signature" -ifaceToHtml :: SourceURLs -> WikiURLs -> Interface -> Bool -> Qualification -> Html -ifaceToHtml maybe_source_url maybe_wiki_url iface unicode qual - = ppModuleContents qual exports (not . null $ ifaceRnOrphanInstances iface) +++ +ifaceToHtml :: SourceURLs -> WikiURLs -> Interface -> Bool -> Maybe Package -> Qualification -> Html +ifaceToHtml maybe_source_url maybe_wiki_url iface unicode pkg qual + = ppModuleContents pkg qual exports (not . null $ ifaceRnOrphanInstances iface) +++ description +++ synopsis +++ divInterface (maybe_doc_hdr +++ bdy +++ orphans) @@ -585,7 +588,7 @@ ifaceToHtml maybe_source_url maybe_wiki_url iface unicode qual description | isNoHtml doc = doc | otherwise = divDescription $ sectionName << "Description" +++ doc - where doc = docSection Nothing qual (ifaceRnDoc iface) + where doc = docSection Nothing pkg qual (ifaceRnDoc iface) -- omit the synopsis if there are no documentation annotations at all synopsis @@ -595,7 +598,7 @@ ifaceToHtml maybe_source_url maybe_wiki_url iface unicode qual collapseDetails "syn" DetailsClosed ( thesummary << "Synopsis" +++ shortDeclList ( - mapMaybe (processExport True linksInfo unicode qual) exports + mapMaybe (processExport True linksInfo unicode pkg qual) exports ) ! collapseToggle "syn" "" ) @@ -609,19 +612,20 @@ ifaceToHtml maybe_source_url maybe_wiki_url iface unicode qual bdy = foldr (+++) noHtml $ - mapMaybe (processExport False linksInfo unicode qual) exports + mapMaybe (processExport False linksInfo unicode pkg qual) exports orphans = - ppOrphanInstances linksInfo (ifaceRnOrphanInstances iface) False unicode qual + ppOrphanInstances linksInfo (ifaceRnOrphanInstances iface) False unicode pkg qual linksInfo = (maybe_source_url, maybe_wiki_url) -ppModuleContents :: Qualification +ppModuleContents :: Maybe Package -- ^ This package + -> Qualification -> [ExportItem DocNameI] - -> Bool -- ^ Orphans sections + -> Bool -- ^ Orphans sections -> Html -ppModuleContents qual exports orphan +ppModuleContents pkg qual exports orphan | null sections && not orphan = noHtml | otherwise = contentsDiv where @@ -641,7 +645,7 @@ ppModuleContents qual exports orphan | otherwise = ( html:secs, rest2 ) where html = linkedAnchor (groupId id0) - << docToHtmlNoAnchors (Just id0) qual (mkMeta doc) +++ mk_subsections ssecs + << docToHtmlNoAnchors (Just id0) pkg qual (mkMeta doc) +++ mk_subsections ssecs (ssecs, rest1) = process lev rest (secs, rest2) = process n rest1 process n (_ : rest) = process n rest @@ -661,22 +665,22 @@ numberSectionHeadings = go 1 = other : go n es -processExport :: Bool -> LinksInfo -> Bool -> Qualification +processExport :: Bool -> LinksInfo -> Bool -> Maybe Package -> Qualification -> ExportItem DocNameI -> Maybe Html -processExport _ _ _ _ ExportDecl { expItemDecl = L _ (InstD {}) } = Nothing -- Hide empty instances -processExport summary _ _ qual (ExportGroup lev id0 doc) - = nothingIf summary $ groupHeading lev id0 << docToHtml (Just id0) qual (mkMeta doc) -processExport summary links unicode qual (ExportDecl decl pats doc subdocs insts fixities splice) - = processDecl summary $ ppDecl summary links decl pats doc insts fixities subdocs splice unicode qual -processExport summary _ _ qual (ExportNoDecl y []) +processExport _ _ _ _ _ ExportDecl { expItemDecl = L _ (InstD {}) } = Nothing -- Hide empty instances +processExport summary _ _ pkg qual (ExportGroup lev id0 doc) + = nothingIf summary $ groupHeading lev id0 << docToHtml (Just id0) pkg qual (mkMeta doc) +processExport summary links unicode pkg qual (ExportDecl decl pats doc subdocs insts fixities splice) + = processDecl summary $ ppDecl summary links decl pats doc insts fixities subdocs splice unicode pkg qual +processExport summary _ _ _ qual (ExportNoDecl y []) = processDeclOneLiner summary $ ppDocName qual Prefix True y -processExport summary _ _ qual (ExportNoDecl y subs) +processExport summary _ _ _ qual (ExportNoDecl y subs) = processDeclOneLiner summary $ ppDocName qual Prefix True y +++ parenList (map (ppDocName qual Prefix True) subs) -processExport summary _ _ qual (ExportDoc doc) - = nothingIf summary $ docSection_ Nothing qual doc -processExport summary _ _ _ (ExportModule mdl) +processExport summary _ _ pkg qual (ExportDoc doc) + = nothingIf summary $ docSection_ Nothing pkg qual doc +processExport summary _ _ _ _ (ExportModule mdl) = processDeclOneLiner summary $ toHtml "module" <+> ppModule mdl @@ -698,7 +702,8 @@ processDeclOneLiner True = Just processDeclOneLiner False = Just . divTopDecl . declElem groupHeading :: Int -> String -> Html -> Html -groupHeading lev id0 = groupTag lev ! [identifier (groupId id0)] +groupHeading lev id0 = linkedAnchor grpId . groupTag lev ! [identifier grpId] + where grpId = groupId id0 groupTag :: Int -> Html -> Html groupTag lev diff --git a/haddock-api/src/Haddock/Backends/Xhtml/Decl.hs b/haddock-api/src/Haddock/Backends/Xhtml/Decl.hs index fe33fbe9..819c9aa6 100644 --- a/haddock-api/src/Haddock/Backends/Xhtml/Decl.hs +++ b/haddock-api/src/Haddock/Backends/Xhtml/Decl.hs @@ -52,36 +52,37 @@ ppDecl :: Bool -- ^ print summary info only -> [(DocName, DocForDecl DocName)] -- ^ documentation for all decls -> Splice -> Unicode -- ^ unicode output + -> Maybe Package -> Qualification -> Html -ppDecl summ links (L loc decl) pats (mbDoc, fnArgsDoc) instances fixities subdocs splice unicode qual = case decl of - TyClD _ (FamDecl _ d) -> ppTyFam summ False links instances fixities loc mbDoc d splice unicode qual - TyClD _ d@(DataDecl {}) -> ppDataDecl summ links instances fixities subdocs loc mbDoc d pats splice unicode qual - TyClD _ d@(SynDecl {}) -> ppTySyn summ links fixities loc (mbDoc, fnArgsDoc) d splice unicode qual - TyClD _ d@(ClassDecl {}) -> ppClassDecl summ links instances fixities loc mbDoc subdocs d splice unicode qual +ppDecl summ links (L loc decl) pats (mbDoc, fnArgsDoc) instances fixities subdocs splice unicode pkg qual = case decl of + TyClD _ (FamDecl _ d) -> ppTyFam summ False links instances fixities loc mbDoc d splice unicode pkg qual + TyClD _ d@(DataDecl {}) -> ppDataDecl summ links instances fixities subdocs loc mbDoc d pats splice unicode pkg qual + TyClD _ d@(SynDecl {}) -> ppTySyn summ links fixities loc (mbDoc, fnArgsDoc) d splice unicode pkg qual + TyClD _ d@(ClassDecl {}) -> ppClassDecl summ links instances fixities loc mbDoc subdocs d splice unicode pkg qual SigD _ (TypeSig _ lnames lty) -> ppLFunSig summ links loc (mbDoc, fnArgsDoc) lnames - (hsSigWcType lty) fixities splice unicode qual + (hsSigWcType lty) fixities splice unicode pkg qual SigD _ (PatSynSig _ lnames lty) -> ppLPatSig summ links loc (mbDoc, fnArgsDoc) lnames - (hsSigType lty) fixities splice unicode qual - ForD _ d -> ppFor summ links loc (mbDoc, fnArgsDoc) d fixities splice unicode qual + (hsSigType lty) fixities splice unicode pkg qual + ForD _ d -> ppFor summ links loc (mbDoc, fnArgsDoc) d fixities splice unicode pkg qual InstD _ _ -> noHtml DerivD _ _ -> noHtml - _ -> error "declaration not supported by ppDecl" + _ -> error "declaration not supported by ppDecl" ppLFunSig :: Bool -> LinksInfo -> SrcSpan -> DocForDecl DocName -> [Located DocName] -> LHsType DocNameI -> [(DocName, Fixity)] -> - Splice -> Unicode -> Qualification -> Html -ppLFunSig summary links loc doc lnames lty fixities splice unicode qual = + Splice -> Unicode -> Maybe Package -> Qualification -> Html +ppLFunSig summary links loc doc lnames lty fixities splice unicode pkg qual = ppFunSig summary links loc doc (map unLoc lnames) lty fixities - splice unicode qual + splice unicode pkg qual ppFunSig :: Bool -> LinksInfo -> SrcSpan -> DocForDecl DocName -> [DocName] -> LHsType DocNameI -> [(DocName, Fixity)] -> - Splice -> Unicode -> Qualification -> Html -ppFunSig summary links loc doc docnames typ fixities splice unicode qual = + Splice -> Unicode -> Maybe Package -> Qualification -> Html +ppFunSig summary links loc doc docnames typ fixities splice unicode pkg qual = ppSigLike summary links loc mempty doc docnames fixities (unLoc typ, pp_typ) - splice unicode qual HideEmptyContexts + splice unicode pkg qual HideEmptyContexts where pp_typ = ppLType unicode qual HideEmptyContexts typ @@ -90,25 +91,25 @@ ppLPatSig :: Bool -> LinksInfo -> SrcSpan -> DocForDecl DocName -> [Located DocName] -- ^ names of patterns in declaration -> LHsType DocNameI -- ^ type of patterns in declaration -> [(DocName, Fixity)] - -> Splice -> Unicode -> Qualification -> Html -ppLPatSig summary links loc doc lnames typ fixities splice unicode qual = + -> Splice -> Unicode -> Maybe Package -> Qualification -> Html +ppLPatSig summary links loc doc lnames typ fixities splice unicode pkg qual = ppSigLike summary links loc (keyword "pattern") doc (map unLoc lnames) fixities - (unLoc typ, pp_typ) splice unicode qual (patSigContext typ) + (unLoc typ, pp_typ) splice unicode pkg qual (patSigContext typ) where pp_typ = ppPatSigType unicode qual typ ppSigLike :: Bool -> LinksInfo -> SrcSpan -> Html -> DocForDecl DocName -> [DocName] -> [(DocName, Fixity)] -> (HsType DocNameI, Html) -> - Splice -> Unicode -> Qualification -> HideEmptyContexts -> Html + Splice -> Unicode -> Maybe Package -> Qualification -> HideEmptyContexts -> Html ppSigLike summary links loc leader doc docnames fixities (typ, pp_typ) - splice unicode qual emptyCtxts = + splice unicode pkg qual emptyCtxts = ppTypeOrFunSig summary links loc docnames typ doc ( addFixities $ leader <+> ppTypeSig summary occnames pp_typ unicode , (leader <+>) . addFixities . concatHtml . punctuate comma $ map (ppBinder False) occnames , dcolon unicode ) - splice unicode qual emptyCtxts + splice unicode pkg qual emptyCtxts where occnames = map (nameOccName . getName) docnames addFixities html @@ -118,13 +119,15 @@ ppSigLike summary links loc leader doc docnames fixities (typ, pp_typ) ppTypeOrFunSig :: Bool -> LinksInfo -> SrcSpan -> [DocName] -> HsType DocNameI -> DocForDecl DocName -> (Html, Html, Html) - -> Splice -> Unicode -> Qualification -> HideEmptyContexts -> Html -ppTypeOrFunSig summary links loc docnames typ (doc, argDocs) (pref1, pref2, sep) splice unicode qual emptyCtxts + -> Splice -> Unicode -> Maybe Package -> Qualification + -> HideEmptyContexts -> Html +ppTypeOrFunSig summary links loc docnames typ (doc, argDocs) (pref1, pref2, sep) + splice unicode pkg qual emptyCtxts | summary = pref1 - | Map.null argDocs = topDeclElem links loc splice docnames pref1 +++ docSection curName qual doc + | Map.null argDocs = topDeclElem links loc splice docnames pref1 +++ docSection curName pkg qual doc | otherwise = topDeclElem links loc splice docnames pref2 - +++ subArguments qual (ppSubSigLike unicode qual typ argDocs [] sep emptyCtxts) - +++ docSection curName qual doc + +++ subArguments pkg qual (ppSubSigLike unicode qual typ argDocs [] sep emptyCtxts) + +++ docSection curName pkg qual doc where curName = getName <$> listToMaybe docnames @@ -225,23 +228,23 @@ tyvarNames = map (getName . hsLTyVarName) . hsQTvExplicit ppFor :: Bool -> LinksInfo -> SrcSpan -> DocForDecl DocName -> ForeignDecl DocNameI -> [(DocName, Fixity)] - -> Splice -> Unicode -> Qualification -> Html + -> Splice -> Unicode -> Maybe Package -> Qualification -> Html ppFor summary links loc doc (ForeignImport _ (L _ name) typ _) fixities - splice unicode qual - = ppFunSig summary links loc doc [name] (hsSigType typ) fixities splice unicode qual -ppFor _ _ _ _ _ _ _ _ _ = error "ppFor" + splice unicode pkg qual + = ppFunSig summary links loc doc [name] (hsSigType typ) fixities splice unicode pkg qual +ppFor _ _ _ _ _ _ _ _ _ _ = error "ppFor" -- we skip type patterns for now ppTySyn :: Bool -> LinksInfo -> [(DocName, Fixity)] -> SrcSpan -> DocForDecl DocName -> TyClDecl DocNameI - -> Splice -> Unicode -> Qualification -> Html + -> Splice -> Unicode -> Maybe Package -> Qualification -> Html ppTySyn summary links fixities loc doc (SynDecl { tcdLName = L _ name, tcdTyVars = ltyvars , tcdRhs = ltype }) - splice unicode qual + splice unicode pkg qual = ppTypeOrFunSig summary links loc [name] (unLoc ltype) doc (full <+> fixs, hdr <+> fixs, spaceHtml +++ equals) - splice unicode qual ShowEmptyToplevelContexts + splice unicode pkg qual ShowEmptyToplevelContexts where hdr = hsep ([keyword "type", ppBinder summary occ] ++ ppTyVars unicode qual (hsQTvExplicit ltyvars)) @@ -250,7 +253,7 @@ ppTySyn summary links fixities loc doc (SynDecl { tcdLName = L _ name, tcdTyVars fixs | summary = noHtml | otherwise = ppFixities fixities qual -ppTySyn _ _ _ _ _ _ _ _ _ = error "declaration not supported by ppTySyn" +ppTySyn _ _ _ _ _ _ _ _ _ _ = error "declaration not supported by ppTySyn" ppTypeSig :: Bool -> [OccName] -> Html -> Unicode -> Html @@ -343,11 +346,13 @@ ppInjectivityAnn unicode qual (InjectivityAnn lhs rhs) = ppTyFam :: Bool -> Bool -> LinksInfo -> [DocInstance DocNameI] -> [(DocName, Fixity)] -> SrcSpan -> Documentation DocName -> - FamilyDecl DocNameI -> Splice -> Unicode -> Qualification -> Html -ppTyFam summary associated links instances fixities loc doc decl splice unicode qual + FamilyDecl DocNameI -> Splice -> Unicode -> Maybe Package -> + Qualification -> Html +ppTyFam summary associated links instances fixities loc doc decl splice unicode + pkg qual | summary = ppTyFamHeader True associated decl unicode qual - | otherwise = header_ +++ docSection Nothing qual doc +++ instancesBit + | otherwise = header_ +++ docSection Nothing pkg qual doc +++ instancesBit where docname = unLoc $ fdLName decl @@ -358,10 +363,10 @@ ppTyFam summary associated links instances fixities loc doc decl splice unicode instancesBit | FamilyDecl { fdInfo = ClosedTypeFamily mb_eqns } <- decl , not summary - = subEquations qual $ map (ppTyFamEqn . unLoc) $ fromMaybe [] mb_eqns + = subEquations pkg qual $ map (ppTyFamEqn . unLoc) $ fromMaybe [] mb_eqns | otherwise - = ppInstances links (OriginFamily docname) instances splice unicode qual + = ppInstances links (OriginFamily docname) instances splice unicode pkg qual -- Individual equation of a closed type family ppTyFamEqn :: TyFamInstEqn DocNameI -> SubDecl @@ -391,9 +396,10 @@ ppPseudoFamilyDecl links splice unicode qual ppAssocType :: Bool -> LinksInfo -> DocForDecl DocName -> LFamilyDecl DocNameI - -> [(DocName, Fixity)] -> Splice -> Unicode -> Qualification -> Html -ppAssocType summ links doc (L loc decl) fixities splice unicode qual = - ppTyFam summ True links [] fixities loc (fst doc) decl splice unicode qual + -> [(DocName, Fixity)] -> Splice -> Unicode -> Maybe Package + -> Qualification -> Html +ppAssocType summ links doc (L loc decl) fixities splice unicode pkg qual = + ppTyFam summ True links [] fixities loc (fst doc) decl splice unicode pkg qual -------------------------------------------------------------------------------- @@ -503,23 +509,23 @@ ppFds fds unicode qual = ppShortClassDecl :: Bool -> LinksInfo -> TyClDecl DocNameI -> SrcSpan -> [(DocName, DocForDecl DocName)] - -> Splice -> Unicode -> Qualification -> Html + -> Splice -> Unicode -> Maybe Package -> Qualification -> Html ppShortClassDecl summary links (ClassDecl { tcdCtxt = lctxt, tcdLName = lname, tcdTyVars = tvs , tcdFDs = fds, tcdSigs = sigs, tcdATs = ats }) loc - subdocs splice unicode qual = + subdocs splice unicode pkg qual = if not (any isUserLSig sigs) && null ats then (if summary then id else topDeclElem links loc splice [nm]) hdr else (if summary then id else topDeclElem links loc splice [nm]) (hdr <+> keyword "where") +++ shortSubDecls False ( - [ ppAssocType summary links doc at [] splice unicode qual | at <- ats + [ ppAssocType summary links doc at [] splice unicode pkg qual | at <- ats , let doc = lookupAnySubdoc (unL $ fdLName $ unL at) subdocs ] ++ -- ToDo: add associated type defaults - [ ppFunSig summary links loc doc names (hsSigWcType typ) - [] splice unicode qual - | L _ (TypeSig _ lnames typ) <- sigs + [ ppFunSig summary links loc doc names (hsSigType typ) + [] splice unicode pkg qual + | L _ (ClassOpSig _ False lnames typ) <- sigs , let doc = lookupAnySubdoc (head names) subdocs names = map unLoc lnames ] -- FIXME: is taking just the first name ok? Is it possible that @@ -529,20 +535,20 @@ ppShortClassDecl summary links (ClassDecl { tcdCtxt = lctxt, tcdLName = lname, t where hdr = ppClassHdr summary lctxt (unLoc lname) tvs fds unicode qual nm = unLoc lname -ppShortClassDecl _ _ _ _ _ _ _ _ = error "declaration type not supported by ppShortClassDecl" +ppShortClassDecl _ _ _ _ _ _ _ _ _ = error "declaration type not supported by ppShortClassDecl" ppClassDecl :: Bool -> LinksInfo -> [DocInstance DocNameI] -> [(DocName, Fixity)] -> SrcSpan -> Documentation DocName -> [(DocName, DocForDecl DocName)] -> TyClDecl DocNameI - -> Splice -> Unicode -> Qualification -> Html + -> Splice -> Unicode -> Maybe Package -> Qualification -> Html ppClassDecl summary links instances fixities loc d subdocs decl@(ClassDecl { tcdCtxt = lctxt, tcdLName = lname, tcdTyVars = ltyvars , tcdFDs = lfds, tcdSigs = lsigs, tcdATs = ats }) - splice unicode qual - | summary = ppShortClassDecl summary links decl loc subdocs splice unicode qual - | otherwise = classheader +++ docSection Nothing qual d + splice unicode pkg qual + | summary = ppShortClassDecl summary links decl loc subdocs splice unicode pkg qual + | otherwise = classheader +++ docSection Nothing pkg qual d +++ minimalBit +++ atBit +++ methodBit +++ instancesBit where sigs = map unLoc lsigs @@ -559,32 +565,32 @@ ppClassDecl summary links instances fixities loc d subdocs hdr = ppClassHdr summary lctxt (unLoc lname) ltyvars lfds -- ToDo: add assocatied typ defaults - atBit = subAssociatedTypes [ ppAssocType summary links doc at subfixs splice unicode qual + atBit = subAssociatedTypes [ ppAssocType summary links doc at subfixs splice unicode pkg qual | at <- ats , let n = unL . fdLName $ unL at doc = lookupAnySubdoc (unL $ fdLName $ unL at) subdocs subfixs = [ f | f@(n',_) <- fixities, n == n' ] ] - methodBit = subMethods [ ppFunSig summary links loc doc names (hsSigType typ) - subfixs splice unicode qual + methodBit = subMethods [ ppFunSig summary links loc doc [name] (hsSigType typ) + subfixs splice unicode pkg qual | L _ (ClassOpSig _ _ lnames typ) <- lsigs - , let doc = lookupAnySubdoc (head names) subdocs - subfixs = [ f | n <- names - , f@(n',_) <- fixities - , n == n' ] - names = map unLoc lnames ] + , name <- map unLoc lnames + , let doc = lookupAnySubdoc name subdocs + subfixs = [ f | f@(n',_) <- fixities + , name == n' ] + ] -- N.B. taking just the first name is ok. Signatures with multiple names -- are expanded so that each name gets its own signature. minimalBit = case [ s | MinimalSig _ _ (L _ s) <- sigs ] of -- Miminal complete definition = every shown method And xs : _ | sort [getName n | L _ (Var (L _ n)) <- xs] == - sort [getName n | TypeSig _ ns _ <- sigs, L _ n <- ns] + sort [getName n | ClassOpSig _ _ ns _ <- sigs, L _ n <- ns] -> noHtml -- Minimal complete definition = the only shown method Var (L _ n) : _ | [getName n] == - [getName n' | L _ (TypeSig _ ns _) <- lsigs, L _ n' <- ns] + [getName n' | L _ (ClassOpSig _ _ ns _) <- lsigs, L _ n' <- ns] -> noHtml -- Minimal complete definition = nothing @@ -600,38 +606,38 @@ ppClassDecl summary links instances fixities loc d subdocs ppMinimal p (Parens x) = ppMinimal p (unLoc x) instancesBit = ppInstances links (OriginClass nm) instances - splice unicode qual + splice unicode pkg qual -ppClassDecl _ _ _ _ _ _ _ _ _ _ _ = error "declaration type not supported by ppShortClassDecl" +ppClassDecl _ _ _ _ _ _ _ _ _ _ _ _ = error "declaration type not supported by ppShortClassDecl" ppInstances :: LinksInfo -> InstOrigin DocName -> [DocInstance DocNameI] - -> Splice -> Unicode -> Qualification + -> Splice -> Unicode -> Maybe Package -> Qualification -> Html -ppInstances links origin instances splice unicode qual - = subInstances qual instName links True (zipWith instDecl [1..] instances) +ppInstances links origin instances splice unicode pkg qual + = subInstances pkg qual instName links True (zipWith instDecl [1..] instances) -- force Splice = True to use line URLs where instName = getOccString origin instDecl :: Int -> DocInstance DocNameI -> (SubDecl,Located DocName) - instDecl no (inst, mdoc, loc) = - ((ppInstHead links splice unicode qual mdoc origin False no inst), loc) + instDecl no (inst, mdoc, loc, mdl) = + ((ppInstHead links splice unicode qual mdoc origin False no inst mdl), loc) ppOrphanInstances :: LinksInfo -> [DocInstance DocNameI] - -> Splice -> Unicode -> Qualification + -> Splice -> Unicode -> Maybe Package -> Qualification -> Html -ppOrphanInstances links instances splice unicode qual - = subOrphanInstances qual links True (zipWith instDecl [1..] instances) +ppOrphanInstances links instances splice unicode pkg qual + = subOrphanInstances pkg qual links True (zipWith instDecl [1..] instances) where instOrigin :: InstHead name -> InstOrigin (IdP name) instOrigin inst = OriginClass (ihdClsName inst) instDecl :: Int -> DocInstance DocNameI -> (SubDecl,Located DocName) - instDecl no (inst, mdoc, loc) = - ((ppInstHead links splice unicode qual mdoc (instOrigin inst) True no inst), loc) + instDecl no (inst, mdoc, loc, mdl) = + ((ppInstHead links splice unicode qual mdoc (instOrigin inst) True no inst mdl), loc) ppInstHead :: LinksInfo -> Splice -> Unicode -> Qualification @@ -640,13 +646,14 @@ ppInstHead :: LinksInfo -> Splice -> Unicode -> Qualification -> Bool -- ^ Is instance orphan -> Int -- ^ Normal -> InstHead DocNameI + -> Maybe Module -> SubDecl -ppInstHead links splice unicode qual mdoc origin orphan no ihd@(InstHead {..}) = +ppInstHead links splice unicode qual mdoc origin orphan no ihd@(InstHead {..}) mdl = case ihdInstType of ClassInst { .. } -> ( subInstHead iid $ ppContextNoLocs clsiCtx unicode qual HideEmptyContexts <+> typ , mdoc - , [subInstDetails iid ats sigs] + , [subInstDetails iid ats sigs mname] ) where sigs = ppInstanceSigs links splice unicode qual clsiSigs @@ -654,7 +661,7 @@ ppInstHead links splice unicode qual mdoc origin orphan no ihd@(InstHead {..}) = TypeInst rhs -> ( subInstHead iid ptype , mdoc - , [subFamInstDetails iid prhs] + , [subFamInstDetails iid prhs mname] ) where ptype = keyword "type" <+> typ @@ -663,11 +670,12 @@ ppInstHead links splice unicode qual mdoc origin orphan no ihd@(InstHead {..}) = DataInst dd -> ( subInstHead iid pdata , mdoc - , [subFamInstDetails iid pdecl]) + , [subFamInstDetails iid pdecl mname]) where pdata = keyword "data" <+> typ pdecl = pdata <+> ppShortDataDecl False True dd [] unicode qual where + mname = maybe noHtml (\m -> toHtml "Defined in" <+> ppModule m) mdl iid = instanceId origin no orphan ihd typ = ppAppNameTypes ihdClsName ihdTypes unicode qual @@ -766,12 +774,12 @@ ppDataDecl :: Bool -> LinksInfo -> Documentation DocName -- ^ this decl's documentation -> TyClDecl DocNameI -- ^ this decl -> [(HsDecl DocNameI, DocForDecl DocName)] -- ^ relevant patterns - -> Splice -> Unicode -> Qualification -> Html + -> Splice -> Unicode -> Maybe Package -> Qualification -> Html ppDataDecl summary links instances fixities subdocs loc doc dataDecl pats - splice unicode qual + splice unicode pkg qual | summary = ppShortDataDecl summary False dataDecl pats unicode qual - | otherwise = header_ +++ docSection Nothing qual doc +++ constrBit +++ patternBit +++ instancesBit + | otherwise = header_ +++ docSection Nothing pkg qual doc +++ constrBit +++ patternBit +++ instancesBit where docname = tcdName dataDecl @@ -792,14 +800,14 @@ ppDataDecl summary links instances fixities subdocs loc doc dataDecl pats | null cons = keyword "where" | otherwise = if isH98 then noHtml else keyword "where" - constrBit = subConstructors qual - [ ppSideBySideConstr subdocs subfixs unicode qual c + constrBit = subConstructors pkg qual + [ ppSideBySideConstr subdocs subfixs unicode pkg qual c | c <- cons , let subfixs = filter (\(n,_) -> any (\cn -> cn == n) (map unLoc (getConNames (unLoc c)))) fixities ] - patternBit = subPatterns qual + patternBit = subPatterns pkg qual [ ppSideBySidePat subfixs unicode qual lnames typ d | (SigD _ (PatSynSig _ lnames typ), d) <- pats , let subfixs = filter (\(n,_) -> any (\cn -> cn == n) @@ -807,7 +815,7 @@ ppDataDecl summary links instances fixities subdocs loc doc dataDecl pats ] instancesBit = ppInstances links (OriginData docname) instances - splice unicode qual + splice unicode pkg qual ppShortConstr :: Bool -> ConDecl DocNameI -> Unicode -> Qualification -> Html @@ -872,10 +880,10 @@ ppShortConstrParts summary dataInst con unicode qual -- | Pretty print an expanded constructor ppSideBySideConstr :: [(DocName, DocForDecl DocName)] -> [(DocName, Fixity)] - -> Unicode -> Qualification + -> Unicode -> Maybe Package -> Qualification -> LConDecl DocNameI -- ^ constructor declaration to print -> SubDecl -ppSideBySideConstr subdocs fixities unicode qual (L _ con) +ppSideBySideConstr subdocs fixities unicode pkg qual (L _ con) = ( decl -- Constructor header (name, fixity) , mbDoc -- Docs on the whole constructor , fieldPart -- Information on the fields (or arguments, if they have docs) @@ -949,10 +957,10 @@ ppSideBySideConstr subdocs fixities unicode qual (L _ con) _ -> [] - doRecordFields fields = subFields qual + doRecordFields fields = subFields pkg qual (map (ppSideBySideField subdocs unicode qual) (map unLoc fields)) - doConstrArgsWithDocs args = subFields qual $ case con of + doConstrArgsWithDocs args = subFields pkg qual $ case con of ConDeclH98{} -> [ (ppLParendType unicode qual HideEmptyContexts arg, mdoc, []) | (i, arg) <- zip [0..] args @@ -1041,7 +1049,7 @@ ppSideBySidePat fixities unicode qual lnames typ (doc, argDocs) = fieldPart | not hasArgDocs = [] - | otherwise = [ subFields qual (ppSubSigLike unicode qual (unLoc patTy) + | otherwise = [ subFields Nothing qual (ppSubSigLike unicode qual (unLoc patTy) argDocs [] (dcolon unicode) emptyCtxt) ] diff --git a/haddock-api/src/Haddock/Backends/Xhtml/DocMarkup.hs b/haddock-api/src/Haddock/Backends/Xhtml/DocMarkup.hs index e63667b0..ed323a90 100644 --- a/haddock-api/src/Haddock/Backends/Xhtml/DocMarkup.hs +++ b/haddock-api/src/Haddock/Backends/Xhtml/DocMarkup.hs @@ -73,7 +73,8 @@ parHtmlMarkup qual insertAnchors ppId = Markup { markupMathDisplay = \mathjax -> toHtml ("\\[" ++ mathjax ++ "\\]"), markupProperty = pre . toHtml, markupExample = examplesToHtml, - markupHeader = \(Header l t) -> makeHeader l t + markupHeader = \(Header l t) -> makeHeader l t, + markupTable = \(Table h r) -> makeTable h r } where makeHeader :: Int -> Html -> Html @@ -85,6 +86,22 @@ parHtmlMarkup qual insertAnchors ppId = Markup { makeHeader 6 mkup = h6 mkup makeHeader l _ = error $ "Somehow got a header level `" ++ show l ++ "' in DocMarkup!" + makeTable :: [TableRow Html] -> [TableRow Html] -> Html + makeTable hs bs = table (concatHtml (hs' ++ bs')) + where + hs' | null hs = [] + | otherwise = [thead (concatHtml (map (makeTableRow th) hs))] + + bs' = [tbody (concatHtml (map (makeTableRow td) bs))] + + makeTableRow :: (Html -> Html) -> TableRow Html -> Html + makeTableRow thr (TableRow cs) = tr (concatHtml (map (makeTableCell thr) cs)) + + makeTableCell :: (Html -> Html) -> TableCell Html -> Html + makeTableCell thr (TableCell i j c) = thr c ! (i' ++ j') + where + i' = if i == 1 then [] else [ colspan i ] + j' = if j == 1 then [] else [ rowspan j ] examplesToHtml l = pre (concatHtml $ map exampleToHtml l) ! [theclass "screen"] @@ -154,10 +171,10 @@ flatten x = [x] -- extract/append the underlying 'Doc' and convert it to 'Html'. For -- 'CollapsingHeader', we attach extra info to the generated 'Html' -- that allows us to expand/collapse the content. -hackMarkup :: DocMarkup id Html -> Hack (ModuleName, OccName) id -> Html -hackMarkup fmt' h' = +hackMarkup :: DocMarkup id Html -> Maybe Package -> Hack (ModuleName, OccName) id -> Html +hackMarkup fmt' currPkg h' = let (html, ms) = hackMarkup' fmt' h' - in html +++ renderMeta fmt' (metaConcat ms) + in html +++ renderMeta fmt' currPkg (metaConcat ms) where hackMarkup' :: DocMarkup id Html -> Hack (ModuleName, OccName) id -> (Html, [Meta]) @@ -176,45 +193,50 @@ hackMarkup fmt' h' = (y, m') = hackMarkup' fmt d' in (markupAppend fmt x y, m ++ m') -renderMeta :: DocMarkup id Html -> Meta -> Html -renderMeta fmt (Meta { _version = Just x }) = +renderMeta :: DocMarkup id Html -> Maybe Package -> Meta -> Html +renderMeta fmt currPkg (Meta { _version = Just x, _package = pkg }) = markupParagraph fmt . markupEmphasis fmt . toHtml $ - "Since: " ++ formatVersion x + "Since: " ++ formatPkgMaybe pkg ++ formatVersion x where formatVersion v = concat . intersperse "." $ map show v -renderMeta _ _ = noHtml + formatPkgMaybe (Just p) | Just p /= currPkg = p ++ "-" + formatPkgMaybe _ = "" +renderMeta _ _ _ = noHtml -- | Goes through 'hackMarkup' to generate the 'Html' rather than -- skipping straight to 'markup': this allows us to employ XHtml -- specific hacks to the tree first. markupHacked :: DocMarkup id Html + -> Maybe Package -- this package -> Maybe String -> MDoc id -> Html -markupHacked fmt n = hackMarkup fmt . toHack 0 n . flatten +markupHacked fmt currPkg n = hackMarkup fmt currPkg . toHack 0 n . flatten -- If the doc is a single paragraph, don't surround it with <P> (this causes -- ugly extra whitespace with some browsers). FIXME: Does this still apply? -docToHtml :: Maybe String -- ^ Name of the thing this doc is for. See - -- comments on 'toHack' for details. +docToHtml :: Maybe String -- ^ Name of the thing this doc is for. See + -- comments on 'toHack' for details. + -> Maybe Package -- ^ Current package -> Qualification -> MDoc DocName -> Html -docToHtml n qual = markupHacked fmt n . cleanup +docToHtml n pkg qual = markupHacked fmt pkg n . cleanup where fmt = parHtmlMarkup qual True (ppDocName qual Raw) -- | Same as 'docToHtml' but it doesn't insert the 'anchor' element -- in links. This is used to generate the Contents box elements. -docToHtmlNoAnchors :: Maybe String -- ^ See 'toHack' +docToHtmlNoAnchors :: Maybe String -- ^ See 'toHack' + -> Maybe Package -- ^ Current package -> Qualification -> MDoc DocName -> Html -docToHtmlNoAnchors n qual = markupHacked fmt n . cleanup +docToHtmlNoAnchors n pkg qual = markupHacked fmt pkg n . cleanup where fmt = parHtmlMarkup qual False (ppDocName qual Raw) -origDocToHtml :: Qualification -> MDoc Name -> Html -origDocToHtml qual = markupHacked fmt Nothing . cleanup +origDocToHtml :: Maybe Package -> Qualification -> MDoc Name -> Html +origDocToHtml pkg qual = markupHacked fmt pkg Nothing . cleanup where fmt = parHtmlMarkup qual True (const $ ppName Raw) -rdrDocToHtml :: Qualification -> MDoc RdrName -> Html -rdrDocToHtml qual = markupHacked fmt Nothing . cleanup +rdrDocToHtml :: Maybe Package -> Qualification -> MDoc RdrName -> Html +rdrDocToHtml pkg qual = markupHacked fmt pkg Nothing . cleanup where fmt = parHtmlMarkup qual True (const ppRdrName) @@ -226,14 +248,17 @@ docElement el content_ = docSection :: Maybe Name -- ^ Name of the thing this doc is for + -> Maybe Package -- ^ Current package -> Qualification -> Documentation DocName -> Html -docSection n qual = maybe noHtml (docSection_ n qual) . combineDocumentation +docSection n pkg qual = + maybe noHtml (docSection_ n pkg qual) . combineDocumentation -docSection_ :: Maybe Name -- ^ Name of the thing this doc is for +docSection_ :: Maybe Name -- ^ Name of the thing this doc is for + -> Maybe Package -- ^ Current package -> Qualification -> MDoc DocName -> Html -docSection_ n qual = - (docElement thediv <<) . docToHtml (getOccString <$> n) qual +docSection_ n pkg qual = + (docElement thediv <<) . docToHtml (getOccString <$> n) pkg qual cleanup :: MDoc a -> MDoc a diff --git a/haddock-api/src/Haddock/Backends/Xhtml/Layout.hs b/haddock-api/src/Haddock/Backends/Xhtml/Layout.hs index e020b909..501caa4b 100644 --- a/haddock-api/src/Haddock/Backends/Xhtml/Layout.hs +++ b/haddock-api/src/Haddock/Backends/Xhtml/Layout.hs @@ -47,7 +47,7 @@ import Haddock.Backends.Xhtml.Utils import Haddock.Types import Haddock.Utils (makeAnchorId, nameAnchorId) import qualified Data.Map as Map -import Text.XHtml hiding ( name, title, p, quote ) +import Text.XHtml hiding ( name, title, quote ) import FastString ( unpackFS ) import GHC @@ -128,38 +128,39 @@ divSubDecls cssClass captionName = maybe noHtml wrap subCaption = paragraph ! [theclass "caption"] << captionName -subDlist :: Qualification -> [SubDecl] -> Maybe Html -subDlist _ [] = Nothing -subDlist qual decls = Just $ ulist << map subEntry decls +subDlist :: Maybe Package -> Qualification -> [SubDecl] -> Maybe Html +subDlist _ _ [] = Nothing +subDlist pkg qual decls = Just $ ulist << map subEntry decls where subEntry (decl, mdoc, subs) = li << (define ! [theclass "src"] << decl +++ - docElement thediv << (fmap (docToHtml Nothing qual) mdoc +++ subs)) + docElement thediv << (fmap (docToHtml Nothing pkg qual) mdoc +++ subs)) -subTable :: Qualification -> [SubDecl] -> Maybe Html -subTable _ [] = Nothing -subTable qual decls = Just $ table << aboves (concatMap subRow decls) +subTable :: Maybe Package -> Qualification -> [SubDecl] -> Maybe Html +subTable _ _ [] = Nothing +subTable pkg qual decls = Just $ table << aboves (concatMap subRow decls) where subRow (decl, mdoc, subs) = (td ! [theclass "src"] << decl <-> - docElement td << fmap (docToHtml Nothing qual) mdoc) + docElement td << fmap (docToHtml Nothing pkg qual) mdoc) : map (cell . (td <<)) subs -- | Sub table with source information (optional). -subTableSrc :: Qualification -> LinksInfo -> Bool -> [(SubDecl,Located DocName)] -> Maybe Html -subTableSrc _ _ _ [] = Nothing -subTableSrc qual lnks splice decls = Just $ table << aboves (concatMap subRow decls) +subTableSrc :: Maybe Package -> Qualification -> LinksInfo -> Bool + -> [(SubDecl,Located DocName)] -> Maybe Html +subTableSrc _ _ _ _ [] = Nothing +subTableSrc pkg qual lnks splice decls = Just $ table << aboves (concatMap subRow decls) where subRow ((decl, mdoc, subs),L loc dn) = (td ! [theclass "src clearfix"] << (thespan ! [theclass "inst-left"] << decl) <+> linkHtml loc dn <-> - docElement td << fmap (docToHtml Nothing qual) mdoc + docElement td << fmap (docToHtml Nothing pkg qual) mdoc ) : map (cell . (td <<)) subs linkHtml loc@(RealSrcSpan _) dn = links lnks loc splice dn @@ -170,49 +171,49 @@ subBlock [] = Nothing subBlock hs = Just $ toHtml hs -subArguments :: Qualification -> [SubDecl] -> Html -subArguments qual = divSubDecls "arguments" "Arguments" . subTable qual +subArguments :: Maybe Package -> Qualification -> [SubDecl] -> Html +subArguments pkg qual = divSubDecls "arguments" "Arguments" . subTable pkg qual subAssociatedTypes :: [Html] -> Html subAssociatedTypes = divSubDecls "associated-types" "Associated Types" . subBlock -subConstructors :: Qualification -> [SubDecl] -> Html -subConstructors qual = divSubDecls "constructors" "Constructors" . subTable qual +subConstructors :: Maybe Package -> Qualification -> [SubDecl] -> Html +subConstructors pkg qual = divSubDecls "constructors" "Constructors" . subTable pkg qual -subPatterns :: Qualification -> [SubDecl] -> Html -subPatterns qual = divSubDecls "bundled-patterns" "Bundled Patterns" . subTable qual +subPatterns :: Maybe Package -> Qualification -> [SubDecl] -> Html +subPatterns pkg qual = divSubDecls "bundled-patterns" "Bundled Patterns" . subTable pkg qual -subFields :: Qualification -> [SubDecl] -> Html -subFields qual = divSubDecls "fields" "Fields" . subDlist qual +subFields :: Maybe Package -> Qualification -> [SubDecl] -> Html +subFields pkg qual = divSubDecls "fields" "Fields" . subDlist pkg qual -subEquations :: Qualification -> [SubDecl] -> Html -subEquations qual = divSubDecls "equations" "Equations" . subTable qual +subEquations :: Maybe Package -> Qualification -> [SubDecl] -> Html +subEquations pkg qual = divSubDecls "equations" "Equations" . subTable pkg qual -- | Generate sub table for instance declarations, with source -subInstances :: Qualification +subInstances :: Maybe Package -> Qualification -> String -- ^ Class name, used for anchor generation -> LinksInfo -> Bool -> [(SubDecl,Located DocName)] -> Html -subInstances qual nm lnks splice = maybe noHtml wrap . instTable +subInstances pkg qual nm lnks splice = maybe noHtml wrap . instTable where wrap contents = subSection (collapseDetails id_ DetailsOpen (summary +++ contents)) - instTable = subTableSrc qual lnks splice + instTable = subTableSrc pkg qual lnks splice subSection = thediv ! [theclass "subs instances"] summary = thesummary << "Instances" id_ = makeAnchorId $ "i:" ++ nm -subOrphanInstances :: Qualification +subOrphanInstances :: Maybe Package -> Qualification -> LinksInfo -> Bool -> [(SubDecl,Located DocName)] -> Html -subOrphanInstances qual lnks splice = maybe noHtml wrap . instTable +subOrphanInstances pkg qual lnks splice = maybe noHtml wrap . instTable where wrap = ((h1 << "Orphan instances") +++) - instTable = fmap (thediv ! [ identifier ("section." ++ id_) ] <<) . subTableSrc qual lnks splice + instTable = fmap (thediv ! [ identifier ("section." ++ id_) ] <<) . subTableSrc pkg qual lnks splice id_ = makeAnchorId $ "orphans" @@ -228,15 +229,17 @@ subInstHead iid hdr = subInstDetails :: String -- ^ Instance unique id (for anchor generation) -> [Html] -- ^ Associated type contents -> [Html] -- ^ Method contents (pretty-printed signatures) + -> Html -- ^ Source module -> Html -subInstDetails iid ats mets = - subInstSection iid << (subAssociatedTypes ats <+> subMethods mets) +subInstDetails iid ats mets mdl = + subInstSection iid << (p mdl <+> subAssociatedTypes ats <+> subMethods mets) subFamInstDetails :: String -- ^ Instance unique id (for anchor generation) -> Html -- ^ Type or data family instance + -> Html -- ^ Source module TODO: use this -> Html -subFamInstDetails iid fi = - subInstSection iid << thediv ! [theclass "src"] << fi +subFamInstDetails iid fi mdl = + subInstSection iid << (p mdl <+> (thediv ! [theclass "src"] << fi)) subInstSection :: String -- ^ Instance unique id (for anchor generation) -> Html diff --git a/haddock-api/src/Haddock/Backends/Xhtml/Names.hs b/haddock-api/src/Haddock/Backends/Xhtml/Names.hs index a84a55e8..574045e0 100644 --- a/haddock-api/src/Haddock/Backends/Xhtml/Names.hs +++ b/haddock-api/src/Haddock/Backends/Xhtml/Names.hs @@ -22,7 +22,7 @@ import Haddock.GhcUtils import Haddock.Types import Haddock.Utils -import Text.XHtml hiding ( name, title, p, quote ) +import Text.XHtml hiding ( name, p, quote ) import qualified Data.Map as M import qualified Data.List as List @@ -147,17 +147,19 @@ linkId mdl mbName = linkIdOcc mdl (fmap nameOccName mbName) True linkIdOcc :: Module -> Maybe OccName -> Bool -> Html -> Html linkIdOcc mdl mbName insertAnchors = if insertAnchors - then anchor ! [href url] + then anchor ! [href url, title ttl] else id where + ttl = moduleNameString (moduleName mdl) url = case mbName of Nothing -> moduleUrl mdl Just name -> moduleNameUrl mdl name linkIdOcc' :: ModuleName -> Maybe OccName -> Html -> Html -linkIdOcc' mdl mbName = anchor ! [href url] +linkIdOcc' mdl mbName = anchor ! [href url, title ttl] where + ttl = moduleNameString mdl url = case mbName of Nothing -> moduleHtmlFile' mdl Just name -> moduleNameUrl' mdl name diff --git a/haddock-api/src/Haddock/Convert.hs b/haddock-api/src/Haddock/Convert.hs index b4804758..4635c076 100644 --- a/haddock-api/src/Haddock/Convert.hs +++ b/haddock-api/src/Haddock/Convert.hs @@ -1,4 +1,3 @@ - {-# LANGUAGE CPP, PatternGuards, TypeFamilies #-} ----------------------------------------------------------------------------- -- | @@ -38,7 +37,7 @@ import Type import TyCoRep import TysPrim ( alphaTyVars ) import TysWiredIn ( listTyConName, starKindTyConName, unitTy ) -import PrelNames ( hasKey, eqTyConKey, funTyConKey, ipClassKey +import PrelNames ( hasKey, eqTyConKey, ipClassKey , tYPETyConKey, liftedRepDataConKey ) import Unique ( getUnique ) import Util ( chkAppend, compareLength, dropList, filterByList, filterOut @@ -168,7 +167,7 @@ synifyTyCon _coax tc -- algebraic data nor newtype: , dd_ctxt = noLoc [] , dd_cType = Nothing - , dd_kindSig = Just (synifyKindSig (tyConKind tc)) + , dd_kindSig = synifyDataTyConReturnKind tc -- we have their kind accurately: , dd_cons = [] -- No constructors , dd_derivs = noLoc [] } @@ -223,7 +222,7 @@ synifyTyCon coax tc -- CoAxioms, not their TyCons _ -> synifyName tc tyvars = synifyTyVars (tyConVisibleTyVars tc) - kindSig = Just (tyConKind tc) + kindSig = synifyDataTyConReturnKind tc -- The data constructors. -- -- Any data-constructors not exported from the module that *defines* the @@ -249,7 +248,7 @@ synifyTyCon coax tc , dd_ND = alg_nd , dd_ctxt = alg_ctx , dd_cType = Nothing - , dd_kindSig = fmap synifyKindSig kindSig + , dd_kindSig = kindSig , dd_cons = cons , dd_derivs = alg_deriv } in case lefts consRaw of @@ -259,6 +258,27 @@ synifyTyCon coax tc , tcdDExt = DataDeclRn False placeHolderNamesTc } dataConErrs -> Left $ unlines dataConErrs +-- In this module, every TyCon being considered has come from an interface +-- file. This means that when considering a data type constructor such as: +-- +-- data Foo (w :: *) (m :: * -> *) (a :: *) +-- +-- Then its tyConKind will be (* -> (* -> *) -> * -> *). But beware! We are +-- also rendering the type variables of Foo, so if we synify the tyConKind of +-- Foo in full, we will end up displaying this in Haddock: +-- +-- data Foo (w :: *) (m :: * -> *) (a :: *) +-- :: * -> (* -> *) -> * -> * +-- +-- Which is entirely wrong (#548). We only want to display the *return* kind, +-- which this function obtains. +synifyDataTyConReturnKind :: TyCon -> Maybe (LHsKind GhcRn) +synifyDataTyConReturnKind tc + = case splitFunTys (tyConKind tc) of + (_, ret_kind) + | isLiftedTypeKind ret_kind -> Nothing -- Don't bother displaying :: * + | otherwise -> Just (synifyKindSig ret_kind) + synifyInjectivityAnn :: Maybe Name -> [TyVar] -> Injectivity -> Maybe (LInjectivityAnn GhcRn) synifyInjectivityAnn Nothing _ _ = Nothing diff --git a/haddock-api/src/Haddock/Interface.hs b/haddock-api/src/Haddock/Interface.hs index cbdf81cb..a66745ea 100644 --- a/haddock-api/src/Haddock/Interface.hs +++ b/haddock-api/src/Haddock/Interface.hs @@ -1,4 +1,4 @@ -{-# LANGUAGE CPP #-} +{-# LANGUAGE CPP, OverloadedStrings #-} ----------------------------------------------------------------------------- -- | -- Module : Haddock.Interface @@ -60,6 +60,7 @@ import FastString (unpackFS) import MonadUtils (liftIO) import TcRnTypes (tcg_rdr_env) import RdrName (plusGlobalRdrEnv) +import ErrUtils (withTiming) #if defined(mingw32_HOST_OS) import System.IO @@ -93,13 +94,15 @@ processModules verbosity modules flags extIfaces = do filter (\i -> not $ OptHide `elem` ifaceOptions i) interfaces mods = Set.fromList $ map ifaceMod interfaces out verbosity verbose "Attaching instances..." - interfaces' <- attachInstances (exportedNames, mods) interfaces instIfaceMap + interfaces' <- {-# SCC attachInstances #-} + withTiming getDynFlags "attachInstances" (const ()) $ do + attachInstances (exportedNames, mods) interfaces instIfaceMap out verbosity verbose "Building cross-linking environment..." -- Combine the link envs of the external packages into one let extLinks = Map.unions (map ifLinkEnv extIfaces) - homeLinks = buildHomeLinks interfaces -- Build the environment for the home - -- package + homeLinks = buildHomeLinks interfaces' -- Build the environment for the home + -- package links = homeLinks `Map.union` extLinks out verbosity verbose "Renaming interfaces..." @@ -155,7 +158,9 @@ createIfaces verbosity flags instIfaceMap mods = do return (reverse ifaces) where f (ifaces, ifaceMap) modSummary = do - x <- processModule verbosity modSummary flags ifaceMap instIfaceMap + x <- {-# SCC processModule #-} + withTiming getDynFlags "processModule" (const ()) $ do + processModule verbosity modSummary flags ifaceMap instIfaceMap return $ case x of Just iface -> (iface:ifaces, Map.insert (ifaceMod iface) iface ifaceMap) Nothing -> (ifaces, ifaceMap) -- Boot modules don't generate ifaces. @@ -164,7 +169,7 @@ createIfaces verbosity flags instIfaceMap mods = do processModule :: Verbosity -> ModSummary -> [Flag] -> IfaceMap -> InstIfaceMap -> Ghc (Maybe Interface) processModule verbosity modsum flags modMap instIfaceMap = do out verbosity verbose $ "Checking module " ++ moduleString (ms_mod modsum) ++ "..." - tm <- loadModule =<< typecheckModule =<< parseModule modsum + tm <- {-# SCC "parse/typecheck/load" #-} loadModule =<< typecheckModule =<< parseModule modsum -- We need to modify the interactive context's environment so that when -- Haddock later looks for instances, it also looks in the modules it @@ -179,8 +184,10 @@ processModule verbosity modsum flags modMap instIfaceMap = do if not $ isBootSummary modsum then do out verbosity verbose "Creating interface..." - (interface, msg) <- runWriterGhc $ createInterface tm flags modMap instIfaceMap - liftIO $ mapM_ putStrLn msg + (interface, msgs) <- {-# SCC createIterface #-} + withTiming getDynFlags "createInterface" (const ()) $ do + runWriterGhc $ createInterface tm flags modMap instIfaceMap + liftIO $ mapM_ putStrLn (nub msgs) dflags <- getDynFlags let (haddockable, haddocked) = ifaceHaddockCoverage interface percentage = round (fromIntegral haddocked * 100 / fromIntegral haddockable :: Double) :: Int diff --git a/haddock-api/src/Haddock/Interface/AttachInstances.hs b/haddock-api/src/Haddock/Interface/AttachInstances.hs index 286907e5..bf50ded3 100644 --- a/haddock-api/src/Haddock/Interface/AttachInstances.hs +++ b/haddock-api/src/Haddock/Interface/AttachInstances.hs @@ -19,7 +19,6 @@ import Haddock.Types import Haddock.Convert import Haddock.GhcUtils -import Control.Applicative import Control.Arrow hiding ((<+>)) import Data.List import Data.Ord (comparing) @@ -70,7 +69,7 @@ attachInstances expInfo ifaces instIfaceMap = do attachOrphanInstances :: ExportInfo -> Interface -> IfaceMap -> InstIfaceMap -> [ClsInst] -> [DocInstance GhcRn] attachOrphanInstances expInfo iface ifaceMap instIfaceMap cls_instances = - [ (synifyInstHead i, instLookup instDocMap n iface ifaceMap instIfaceMap, (L (getSrcSpan n) n)) + [ (synifyInstHead i, instLookup instDocMap n iface ifaceMap instIfaceMap, (L (getSrcSpan n) n), Nothing) | let is = [ (instanceSig i, getName i) | i <- cls_instances, isOrphan (is_orphan i) ] , (i@(_,_,cls,tys), n) <- sortBy (comparing $ first instHead) is , not $ isInstanceHidden expInfo cls tys @@ -92,7 +91,11 @@ attachToExportItem index expInfo iface ifaceMap instIfaceMap export = let mb_instances = lookupNameEnv index (tcdName d) cls_instances = maybeToList mb_instances >>= fst fam_instances = maybeToList mb_instances >>= snd - fam_insts = [ (synifyFamInst i opaque, doc,spanNameE n (synifyFamInst i opaque) (L eSpan (tcdName d)) ) + fam_insts = [ ( synifyFamInst i opaque + , doc + , spanNameE n (synifyFamInst i opaque) (L eSpan (tcdName d)) + , nameModule_maybe n + ) | i <- sortBy (comparing instFam) fam_instances , let n = getName i , let doc = instLookup instDocMap n iface ifaceMap instIfaceMap @@ -100,14 +103,18 @@ attachToExportItem index expInfo iface ifaceMap instIfaceMap export = , not $ any (isTypeHidden expInfo) (fi_tys i) , let opaque = isTypeHidden expInfo (fi_rhs i) ] - cls_insts = [ (synifyInstHead i, instLookup instDocMap n iface ifaceMap instIfaceMap, spanName n (synifyInstHead i) (L eSpan (tcdName d))) + cls_insts = [ ( synifyInstHead i + , instLookup instDocMap n iface ifaceMap instIfaceMap + , spanName n (synifyInstHead i) (L eSpan (tcdName d)) + , nameModule_maybe n + ) | let is = [ (instanceSig i, getName i) | i <- cls_instances ] , (i@(_,_,cls,tys), n) <- sortBy (comparing $ first instHead) is , not $ isInstanceHidden expInfo cls tys ] -- fam_insts but with failing type fams filtered out - cleanFamInsts = [ (fi, n, L l r) | (Right fi, n, L l (Right r)) <- fam_insts ] - famInstErrs = [ errm | (Left errm, _, _) <- fam_insts ] + cleanFamInsts = [ (fi, n, L l r, m) | (Right fi, n, L l (Right r), m) <- fam_insts ] + famInstErrs = [ errm | (Left errm, _, _, _) <- fam_insts ] in do dfs <- getDynFlags let mkBug = (text "haddock-bug:" <+>) . text diff --git a/haddock-api/src/Haddock/Interface/Create.hs b/haddock-api/src/Haddock/Interface/Create.hs index 78b5c36d..78242990 100644 --- a/haddock-api/src/Haddock/Interface/Create.hs +++ b/haddock-api/src/Haddock/Interface/Create.hs @@ -46,7 +46,6 @@ import Data.Traversable import Avail hiding (avail) import qualified Avail -import qualified Packages import qualified Module import qualified SrcLoc import ConLike (ConLike(..)) @@ -55,10 +54,11 @@ import HscTypes import Name import NameSet import NameEnv +import Packages ( lookupModuleInAllPackages, PackageName(..) ) import Bag import RdrName import TcRnTypes -import FastString (fastStringToByteString) +import FastString ( unpackFS, fastStringToByteString) import BasicTypes ( StringLiteral(..), SourceText(..) ) import qualified Outputable as O import HsDecls ( getConArgs ) @@ -85,12 +85,22 @@ createInterface tm flags modMap instIfaceMap = do !instances = modInfoInstances mi !fam_instances = md_fam_insts md !exportedNames = modInfoExportsWithSelectors mi + (pkgNameFS, _) = modulePackageInfo dflags flags mdl + pkgName = fmap (unpackFS . (\(PackageName n) -> n)) pkgNameFS (TcGblEnv { tcg_rdr_env = gre , tcg_warns = warnings , tcg_exports = all_exports }, md) = tm_internals_ tm + -- The 'pkgName' is necessary to decide what package to mention in "@since" + -- annotations. Not having it is not fatal though. + -- + -- Cabal can be trusted to pass the right flags, so this warning should be + -- mostly encountered when running Haddock outside of Cabal. + when (isNothing pkgName) $ + liftErrMsg $ tell [ "Warning: Package name is not available." ] + -- The renamed source should always be available to us, but it's best -- to be on the safe side. (group_, imports, mayExports, mayDocHeader) <- @@ -103,7 +113,7 @@ createInterface tm flags modMap instIfaceMap = do opts <- liftErrMsg $ mkDocOpts (haddockOptions dflags) flags mdl -- Process the top-level module header documentation. - (!info, mbDoc) <- liftErrMsg $ processModuleHeader dflags gre safety mayDocHeader + (!info, mbDoc) <- liftErrMsg $ processModuleHeader dflags pkgName gre safety mayDocHeader let declsWithDocs = topDecls group_ @@ -130,13 +140,13 @@ createInterface tm flags modMap instIfaceMap = do warningMap <- liftErrMsg (mkWarningMap dflags warnings gre exportedNames) maps@(!docMap, !argMap, !declMap, _) <- - liftErrMsg (mkMaps dflags gre localInsts declsWithDocs) + liftErrMsg (mkMaps dflags pkgName gre localInsts declsWithDocs) let allWarnings = M.unions (warningMap : map ifaceWarningMap (M.elems modMap)) -- The MAIN functionality: compute the export items which will -- each be the actual documentation of this module. - exportItems <- mkExportItems is_sig modMap mdl sem_mdl allWarnings gre + exportItems <- mkExportItems is_sig modMap pkgName mdl sem_mdl allWarnings gre exportedNames decls maps fixMap unrestrictedImportedMods splices exports all_exports instIfaceMap dflags @@ -160,7 +170,7 @@ createInterface tm flags modMap instIfaceMap = do modWarn <- liftErrMsg (moduleWarning dflags gre warnings) - tokenizedSrc <- mkMaybeTokenizedSrc flags tm + tokenizedSrc <- mkMaybeTokenizedSrc dflags flags tm return $! Interface { ifaceMod = mdl @@ -190,6 +200,7 @@ createInterface tm flags modMap instIfaceMap = do , ifaceTokenizedSrc = tokenizedSrc } + -- | Given all of the @import M as N@ declarations in a package, -- create a mapping from the module identity of M, to an alias N -- (if there are multiple aliases, we pick the last one.) This @@ -266,7 +277,7 @@ lookupModuleDyn :: lookupModuleDyn _ (Just pkgId) mdlName = Module.mkModule pkgId mdlName lookupModuleDyn dflags Nothing mdlName = - case Packages.lookupModuleInAllPackages dflags mdlName of + case lookupModuleInAllPackages dflags mdlName of (m,_):_ -> m [] -> Module.mkModule Module.mainUnitId mdlName @@ -314,16 +325,17 @@ mkDocOpts mbOpts flags mdl = do [] -> tell ["No option supplied to DOC_OPTION/doc_option"] >> return [] xs -> liftM catMaybes (mapM parseOption xs) Nothing -> return [] - hm <- if Flag_HideModule (moduleString mdl) `elem` flags - then return $ OptHide : opts - else return opts - ie <- if Flag_IgnoreAllExports `elem` flags - then return $ OptIgnoreExports : hm - else return hm - se <- if Flag_ShowExtensions (moduleString mdl) `elem` flags - then return $ OptShowExtensions : ie - else return ie - return se + pure (foldl go opts flags) + where + mdlStr = moduleString mdl + + -- Later flags override earlier ones + go os m | m == Flag_HideModule mdlStr = OptHide : os + | m == Flag_ShowModule mdlStr = filter (/= OptHide) os + | m == Flag_ShowAllModules = filter (/= OptHide) os + | m == Flag_IgnoreAllExports = OptIgnoreExports : os + | m == Flag_ShowExtensions mdlStr = OptIgnoreExports : os + | otherwise = os parseOption :: String -> ErrMsgM (Maybe DocOption) parseOption "hide" = return (Just OptHide) @@ -345,11 +357,12 @@ type Maps = (DocMap Name, ArgMap Name, DeclMap, InstMap) -- find its names, its subordinates, and its doc strings. Process doc strings -- into 'Doc's. mkMaps :: DynFlags + -> Maybe Package -- this package -> GlobalRdrEnv -> [Name] -> [(LHsDecl GhcRn, [HsDocString])] -> ErrMsgM Maps -mkMaps dflags gre instances decls = do +mkMaps dflags pkgName gre instances decls = do (a, b, c) <- unzip3 <$> traverse mappings decls pure ( f' (map (nubByName fst) a) , f (filterMapping (not . M.null) b) @@ -376,8 +389,8 @@ mkMaps dflags gre instances decls = do declDoc :: [HsDocString] -> Map Int HsDocString -> ErrMsgM (Maybe (MDoc Name), Map Int (MDoc Name)) declDoc strs m = do - doc' <- processDocStrings dflags gre strs - m' <- traverse (processDocStringParas dflags gre) m + doc' <- processDocStrings dflags pkgName gre strs + m' <- traverse (processDocStringParas dflags pkgName gre) m pure (doc', m') (doc, args) <- declDoc docStrs (declTypeDocs decl) @@ -515,7 +528,8 @@ classDecls class_ = filterDecls . collectDocs . sortByLoc $ decls -- | The top-level declarations of a module that we care about, -- ordered by source location, with documentation attached if it exists. topDecls :: HsGroup GhcRn -> [(LHsDecl GhcRn, [HsDocString])] -topDecls = filterClasses . filterDecls . collectDocs . sortByLoc . ungroup +topDecls = + filterClasses . filterDecls . collectDocs . sortByLoc . ungroup -- | Extract a map of fixity declarations only mkFixMap :: HsGroup GhcRn -> FixMap @@ -575,7 +589,6 @@ filterDecls = filter (isHandled . unL . fst) isHandled (DocD {}) = True isHandled _ = False - -- | Go through all class declarations and filter their sub-declarations filterClasses :: [(LHsDecl a, doc)] -> [(LHsDecl a, doc)] filterClasses decls = [ if isClassD d then (L loc (filterClass d), doc) else x @@ -620,12 +633,13 @@ collectDocs = go Nothing [] mkExportItems :: Bool -- is it a signature -> IfaceMap + -> Maybe Package -- this package -> Module -- this module -> Module -- semantic module -> WarningMap -> GlobalRdrEnv -> [Name] -- exported names (orig) - -> [LHsDecl GhcRn] -- renamed source declarations + -> [LHsDecl GhcRn] -- renamed source declarations -> Maps -> FixMap -> M.Map ModuleName [ModuleName] @@ -636,13 +650,14 @@ mkExportItems -> DynFlags -> ErrMsgGhc [ExportItem GhcRn] mkExportItems - is_sig modMap thisMod semMod warnings gre exportedNames decls + is_sig modMap pkgName thisMod semMod warnings gre exportedNames decls maps fixMap unrestricted_imp_mods splices exportList allExports instIfaceMap dflags = case exportList of Nothing -> - fullModuleContents is_sig modMap thisMod semMod warnings exportedNames - decls maps fixMap splices instIfaceMap dflags allExports + fullModuleContents is_sig modMap pkgName thisMod semMod warnings gre + exportedNames decls maps fixMap splices instIfaceMap dflags + allExports Just exports -> liftM concat $ mapM lookupExport exports where lookupExport (IEGroup _ lev docStr, _) = liftErrMsg $ do @@ -650,14 +665,14 @@ mkExportItems return [ExportGroup lev "" doc] lookupExport (IEDoc _ docStr, _) = liftErrMsg $ do - doc <- processDocStringParas dflags gre docStr + doc <- processDocStringParas dflags pkgName gre docStr return [ExportDoc doc] lookupExport (IEDocNamed _ str, _) = liftErrMsg $ findNamedDoc str [ unL d | d <- decls ] >>= \case Nothing -> return [] Just docStr -> do - doc <- processDocStringParas dflags gre docStr + doc <- processDocStringParas dflags pkgName gre docStr return [ExportDoc doc] lookupExport (IEModuleContents _ (L _ mod_name), _) @@ -976,9 +991,11 @@ moduleExport thisMod dflags ifaceMap instIfaceMap expMod = fullModuleContents :: Bool -- is it a signature -> IfaceMap + -> Maybe Package -- this package -> Module -- this module -> Module -- semantic module -> WarningMap + -> GlobalRdrEnv -- ^ The renaming environment -> [Name] -- exported names (orig) -> [LHsDecl GhcRn] -- renamed source declarations -> Maps @@ -988,23 +1005,29 @@ fullModuleContents :: Bool -- is it a signature -> DynFlags -> Avails -> ErrMsgGhc [ExportItem GhcRn] -fullModuleContents is_sig modMap thisMod semMod warnings exportedNames +fullModuleContents is_sig modMap pkgName thisMod semMod warnings gre exportedNames decls maps@(_, _, declMap, _) fixMap splices instIfaceMap dflags avails = do let availEnv = availsToNameEnv (nubAvails avails) (concat . concat) `fmap` (for decls $ \decl -> do - for (getMainDeclBinder (unLoc decl)) $ \nm -> do - case lookupNameEnv availEnv nm of - Just avail - | L _ (ValD _ valDecl) <- decl - , (name:_) <- collectHsBindBinders valDecl - , Just (L _ SigD{}:_) <- filter isSigD <$> M.lookup name declMap - -> pure [] - - | otherwise - -> availExportItem is_sig modMap thisMod - semMod warnings exportedNames maps fixMap - splices instIfaceMap dflags avail - Nothing -> pure []) + case decl of + (L _ (DocD _ (DocGroup lev docStr))) -> do + doc <- liftErrMsg (processDocString dflags gre docStr) + return [[ExportGroup lev "" doc]] + (L _ (DocD _ (DocCommentNamed _ docStr))) -> do + doc <- liftErrMsg (processDocStringParas dflags pkgName gre docStr) + return [[ExportDoc doc]] + (L _ (ValD _ valDecl)) + | name:_ <- collectHsBindBinders valDecl + , Just (L _ SigD{}:_) <- filter isSigD <$> M.lookup name declMap + -> return [] + _ -> + for (getMainDeclBinder (unLoc decl)) $ \nm -> do + case lookupNameEnv availEnv nm of + Just avail -> + availExportItem is_sig modMap thisMod + semMod warnings exportedNames maps fixMap + splices instIfaceMap dflags avail + Nothing -> pure []) where isSigD (L _ SigD{}) = True isSigD _ = False @@ -1061,19 +1084,32 @@ extractDecl declMap name decl FamEqn { feqn_tycon = L _ n , feqn_pats = tys , feqn_rhs = defn }}))) -> - SigD noExt <$> extractRecSel name n tys (dd_cons defn) - InstD _ (ClsInstD _ ClsInstDecl { cid_datafam_insts = insts }) -> - let matches = [ d' | L _ d'@(DataFamInstDecl (HsIB { hsib_body = d })) - <- insts - -- , L _ ConDecl { con_details = RecCon rec } <- dd_cons (feqn_rhs d) - , RecCon rec <- map (getConArgs . unLoc) (dd_cons (feqn_rhs d)) - , ConDeclField { cd_fld_names = ns } <- map unLoc (unLoc rec) - , L _ n <- ns - , extFieldOcc n == name - ] - in case matches of - [d0] -> extractDecl declMap name (noLoc . InstD noExt $ DataFamInstD noExt d0) - _ -> error "internal: extractDecl (ClsInstD)" + if isDataConName name + then SigD noExt <$> extractPatternSyn name n tys (dd_cons defn) + else SigD noExt <$> extractRecSel name n tys (dd_cons defn) + InstD _ (ClsInstD _ ClsInstDecl { cid_datafam_insts = insts }) + | isDataConName name -> + let matches = [ d' | L _ d'@(DataFamInstDecl (HsIB { hsib_body = + FamEqn { feqn_rhs = dd + } + })) <- insts + , name `elem` map unLoc (concatMap (getConNames . unLoc) (dd_cons dd)) + ] + in case matches of + [d0] -> extractDecl declMap name (noLoc (InstD noExt (DataFamInstD noExt d0))) + _ -> error "internal: extractDecl (ClsInstD)" + | otherwise -> + let matches = [ d' | L _ d'@(DataFamInstDecl (HsIB { hsib_body = d })) + <- insts + -- , L _ ConDecl { con_details = RecCon rec } <- dd_cons (feqn_rhs d) + , RecCon rec <- map (getConArgs . unLoc) (dd_cons (feqn_rhs d)) + , ConDeclField { cd_fld_names = ns } <- map unLoc (unLoc rec) + , L _ n <- ns + , extFieldOcc n == name + ] + in case matches of + [d0] -> extractDecl declMap name (noLoc . InstD noExt $ DataFamInstD noExt d0) + _ -> error "internal: extractDecl (ClsInstD)" _ -> error "internal: extractDecl" @@ -1153,12 +1189,12 @@ seqList :: [a] -> () seqList [] = () seqList (x : xs) = x `seq` seqList xs -mkMaybeTokenizedSrc :: [Flag] -> TypecheckedModule +mkMaybeTokenizedSrc :: DynFlags -> [Flag] -> TypecheckedModule -> ErrMsgGhc (Maybe [RichToken]) -mkMaybeTokenizedSrc flags tm +mkMaybeTokenizedSrc dflags flags tm | Flag_HyperlinkedSource `elem` flags = case renamedSource tm of Just src -> do - tokens <- liftGhcToErrMsgGhc . liftIO $ mkTokenizedSrc summary src + tokens <- liftGhcToErrMsgGhc (liftIO (mkTokenizedSrc dflags summary src)) return $ Just tokens Nothing -> do liftErrMsg . tell . pure $ concat @@ -1171,12 +1207,15 @@ mkMaybeTokenizedSrc flags tm where summary = pm_mod_summary . tm_parsed_module $ tm -mkTokenizedSrc :: ModSummary -> RenamedSource -> IO [RichToken] -mkTokenizedSrc ms src = do +mkTokenizedSrc :: DynFlags -> ModSummary -> RenamedSource -> IO [RichToken] +mkTokenizedSrc dflags ms src = do -- make sure to read the whole file at once otherwise -- we run out of file descriptors (see #495) rawSrc <- BS.readFile (msHsFilePath ms) >>= evaluate - return $ Hyperlinker.enrich src (Hyperlinker.parse (decodeUtf8 rawSrc)) + let tokens = Hyperlinker.parse dflags filepath (Utf8.decodeUtf8 rawSrc) + return $ Hyperlinker.enrich src tokens + where + filepath = msHsFilePath ms -- | Find a stand-alone documentation comment by its name. findNamedDoc :: String -> [HsDecl GhcRn] -> ErrMsgM (Maybe HsDocString) diff --git a/haddock-api/src/Haddock/Interface/LexParseRn.hs b/haddock-api/src/Haddock/Interface/LexParseRn.hs index ce1dbc62..731f2a35 100644 --- a/haddock-api/src/Haddock/Interface/LexParseRn.hs +++ b/haddock-api/src/Haddock/Interface/LexParseRn.hs @@ -18,50 +18,48 @@ module Haddock.Interface.LexParseRn , processModuleHeader ) where -import Data.IntSet (toList) import Data.List import Documentation.Haddock.Doc (metaDocConcat) import DynFlags (languageExtensions) import qualified GHC.LanguageExtensions as LangExt -import FastString import GHC import Haddock.Interface.ParseModuleHeader import Haddock.Parser import Haddock.Types import Name -import Outputable ( showPpr ) +import Outputable ( showPpr, showSDoc ) import RdrName import EnumSet import RnEnv (dataTcOccs) -processDocStrings :: DynFlags -> GlobalRdrEnv -> [HsDocString] +processDocStrings :: DynFlags -> Maybe Package -> GlobalRdrEnv -> [HsDocString] -> ErrMsgM (Maybe (MDoc Name)) -processDocStrings dflags gre strs = do - mdoc <- metaDocConcat <$> traverse (processDocStringParas dflags gre) strs +processDocStrings dflags pkg gre strs = do + mdoc <- metaDocConcat <$> traverse (processDocStringParas dflags pkg gre) strs case mdoc of -- We check that we don't have any version info to render instead -- of just checking if there is no comment: there may not be a -- comment but we still want to pass through any meta data. - MetaDoc { _meta = Meta { _version = Nothing }, _doc = DocEmpty } -> pure Nothing + MetaDoc { _meta = Meta Nothing Nothing, _doc = DocEmpty } -> pure Nothing x -> pure (Just x) -processDocStringParas :: DynFlags -> GlobalRdrEnv -> HsDocString -> ErrMsgM (MDoc Name) -processDocStringParas dflags gre hds = - overDocF (rename dflags gre) $ parseParas dflags (unpackHDS hds) +processDocStringParas :: DynFlags -> Maybe Package -> GlobalRdrEnv -> HsDocString -> ErrMsgM (MDoc Name) +processDocStringParas dflags pkg gre hds = + overDocF (rename dflags gre) $ parseParas dflags pkg (unpackHDS hds) processDocString :: DynFlags -> GlobalRdrEnv -> HsDocString -> ErrMsgM (Doc Name) processDocString dflags gre hds = rename dflags gre $ parseString dflags (unpackHDS hds) -processModuleHeader :: DynFlags -> GlobalRdrEnv -> SafeHaskellMode -> Maybe LHsDocString +processModuleHeader :: DynFlags -> Maybe Package -> GlobalRdrEnv -> SafeHaskellMode -> Maybe LHsDocString -> ErrMsgM (HaddockModInfo Name, Maybe (MDoc Name)) -processModuleHeader dflags gre safety mayStr = do +processModuleHeader dflags pkgName gre safety mayStr = do (hmi, doc) <- case mayStr of Nothing -> return failure Just (L _ hds) -> do let str = unpackHDS hds - (hmi, doc) = parseModuleHeader dflags str + (hmi, doc) = parseModuleHeader dflags pkgName str !descr <- case hmi_description hmi of Just hmi_descr -> Just <$> rename dflags gre hmi_descr Nothing -> pure Nothing @@ -104,7 +102,9 @@ rename dflags gre = rn -- We found no names in the env so we start guessing. [] -> case choices of + -- This shouldn't happen as 'dataTcOccs' always returns at least its input. [] -> pure (DocMonospaced (DocString (showPpr dflags x))) + -- There was nothing in the environment so we need to -- pick some default from what's available to us. We -- diverge here from the old way where we would default @@ -113,16 +113,16 @@ rename dflags gre = rn -- type constructor names (such as in #253). So now we -- only get type constructor links if they are actually -- in scope. - a:_ -> pure (outOfScope dflags a) + a:_ -> outOfScope dflags a -- There is only one name in the environment that matches so -- use it. [a] -> pure (DocIdentifier a) + -- But when there are multiple names available, default to -- type constructors: somewhat awfully GHC returns the -- values in the list positionally. - a:b:_ | isTyConName a -> pure (DocIdentifier a) - | otherwise -> pure (DocIdentifier b) + a:b:_ -> ambiguous dflags x (if isTyConName a then a else b) names DocWarning doc -> DocWarning <$> rn doc DocEmphasis doc -> DocEmphasis <$> rn doc @@ -144,6 +144,7 @@ rename dflags gre = rn DocEmpty -> pure (DocEmpty) DocString str -> pure (DocString str) DocHeader (Header l t) -> DocHeader . Header l <$> rn t + DocTable t -> DocTable <$> traverse rn t -- | Wrap an identifier that's out of scope (i.e. wasn't found in -- 'GlobalReaderEnv' during 'rename') in an appropriate doc. Currently @@ -153,12 +154,29 @@ rename dflags gre = rn -- users shouldn't rely on this doing the right thing. See tickets -- #253 and #375 on the confusion this causes depending on which -- default we pick in 'rename'. -outOfScope :: DynFlags -> RdrName -> Doc a +outOfScope :: DynFlags -> RdrName -> ErrMsgM (Doc a) outOfScope dflags x = case x of - Unqual occ -> monospaced occ - Qual mdl occ -> DocIdentifierUnchecked (mdl, occ) - Orig _ occ -> monospaced occ - Exact name -> monospaced name -- Shouldn't happen since x is out of scope + Unqual occ -> warnAndMonospace occ + Qual mdl occ -> pure (DocIdentifierUnchecked (mdl, occ)) + Orig _ occ -> warnAndMonospace occ + Exact name -> warnAndMonospace name -- Shouldn't happen since x is out of scope where + warnAndMonospace a = do + tell ["Warning: '" ++ showPpr dflags a ++ "' is out of scope."] + pure (monospaced a) monospaced a = DocMonospaced (DocString (showPpr dflags a)) + +-- | Warn about an ambiguous identifier. +ambiguous :: DynFlags -> RdrName -> Name -> [Name] -> ErrMsgM (Doc Name) +ambiguous dflags x dflt names = do + tell [msg] + pure (DocIdentifier dflt) + where + msg = "Warning: " ++ x_str ++ " is ambiguous. It is defined\n" ++ + concatMap (\n -> " * " ++ defnLoc n ++ "\n") names ++ + " You may be able to disambiguate the identifier by qualifying it or\n" ++ + " by hiding some imports.\n" ++ + " Defaulting to " ++ x_str ++ " defined " ++ defnLoc dflt + x_str = '\'' : showPpr dflags x ++ "'" + defnLoc = showSDoc dflags . pprNameDefnLoc diff --git a/haddock-api/src/Haddock/Interface/ParseModuleHeader.hs b/haddock-api/src/Haddock/Interface/ParseModuleHeader.hs index 768a31ce..050901b6 100644 --- a/haddock-api/src/Haddock/Interface/ParseModuleHeader.hs +++ b/haddock-api/src/Haddock/Interface/ParseModuleHeader.hs @@ -24,8 +24,8 @@ import RdrName -- NB. The headers must be given in the order Module, Description, -- Copyright, License, Maintainer, Stability, Portability, except that -- any or all may be omitted. -parseModuleHeader :: DynFlags -> String -> (HaddockModInfo RdrName, MDoc RdrName) -parseModuleHeader dflags str0 = +parseModuleHeader :: DynFlags -> Maybe Package -> String -> (HaddockModInfo RdrName, MDoc RdrName) +parseModuleHeader dflags pkgName str0 = let getKey :: String -> String -> (Maybe String,String) getKey key str = case parseKey key str of @@ -37,21 +37,22 @@ parseModuleHeader dflags str0 = (copyrightOpt,str3) = getKey "Copyright" str2 (licenseOpt,str4) = getKey "License" str3 (licenceOpt,str5) = getKey "Licence" str4 - (maintainerOpt,str6) = getKey "Maintainer" str5 - (stabilityOpt,str7) = getKey "Stability" str6 - (portabilityOpt,str8) = getKey "Portability" str7 + (spdxLicenceOpt,str6) = getKey "SPDX-License-Identifier" str5 + (maintainerOpt,str7) = getKey "Maintainer" str6 + (stabilityOpt,str8) = getKey "Stability" str7 + (portabilityOpt,str9) = getKey "Portability" str8 in (HaddockModInfo { hmi_description = parseString dflags <$> descriptionOpt, hmi_copyright = copyrightOpt, - hmi_license = licenseOpt `mplus` licenceOpt, + hmi_license = spdxLicenceOpt `mplus` licenseOpt `mplus` licenceOpt, hmi_maintainer = maintainerOpt, hmi_stability = stabilityOpt, hmi_portability = portabilityOpt, hmi_safety = Nothing, hmi_language = Nothing, -- set in LexParseRn hmi_extensions = [] -- also set in LexParseRn - }, parseParas dflags str8) + }, parseParas dflags pkgName str9) -- | This function is how we read keys. -- diff --git a/haddock-api/src/Haddock/Interface/Rename.hs b/haddock-api/src/Haddock/Interface/Rename.hs index e3e4e987..c07f8300 100644 --- a/haddock-api/src/Haddock/Interface/Rename.hs +++ b/haddock-api/src/Haddock/Interface/Rename.hs @@ -22,6 +22,8 @@ import Bag (emptyBag) import GHC hiding (NoLink) import Name import Outputable ( panic ) +import RdrName (RdrName(Exact)) +import PrelNames (eqTyCon_RDR) import Control.Applicative import Control.Monad hiding (mapM) @@ -60,11 +62,18 @@ renameInterface dflags renamingEnv warnings iface = (missingNames1 ++ missingNames2 ++ missingNames3 ++ missingNames4 ++ missingNames5) - -- filter out certain built in type constructors using their string - -- representation. TODO: use the Name constants from the GHC API. --- strings = filter (`notElem` ["()", "[]", "(->)"]) --- (map pretty missingNames) - strings = map (pretty dflags) . filter (\n -> not (isSystemName n || isBuiltInSyntax n)) $ missingNames + -- Filter out certain built in type constructors using their string + -- representation. + -- + -- Note that since the renamed AST represents equality constraints as + -- @HasOpTy t1 eqTyCon_RDR t2@ (and _not_ as @HsEqTy t1 t2@), we need to + -- manually filter out 'eqTyCon_RDR' (aka @~@). + strings = [ pretty dflags n + | n <- missingNames + , not (isSystemName n) + , not (isBuiltInSyntax n) + , Exact n /= eqTyCon_RDR + ] in do -- report things that we couldn't link to. Only do this for non-hidden @@ -263,11 +272,22 @@ renameType t = case t of HsRecTy _ a -> HsRecTy NoExt <$> mapM renameConDeclFieldField a (XHsType (NHsCoreTy a)) -> pure (XHsType (NHsCoreTy a)) - HsExplicitListTy x i b -> HsExplicitListTy x i <$> mapM renameLType b - HsExplicitTupleTy x b -> HsExplicitTupleTy x <$> mapM renameLType b - HsSpliceTy _ _ -> error "renameType: HsSpliceTy" - HsWildCardTy a -> HsWildCardTy <$> renameWildCardInfo a - HsAppsTy _ _ -> error "renameType: HsAppsTy" + HsExplicitListTy i a b -> HsExplicitListTy i a <$> mapM renameLType b + HsExplicitTupleTy a b -> HsExplicitTupleTy a <$> mapM renameLType b + HsSpliceTy _ s -> renameHsSpliceTy s + HsWildCardTy a -> HsWildCardTy <$> renameWildCardInfo a + HsAppsTy _ _ -> error "renameType: HsAppsTy" + +-- | Rename splices, but _only_ those that turn out to be for types. +-- I think this is actually safe for our possible inputs: +-- +-- * the input is from after GHC's renamer, so should have an 'HsSpliced' +-- * the input is typechecked, and only 'HsSplicedTy' should get through that +-- +renameHsSpliceTy :: HsSplice GhcRn -> RnM (HsType DocNameI) +renameHsSpliceTy (HsSpliced _ _ (HsSplicedTy t)) = renameType t +renameHsSpliceTy (HsSpliced _ _ _) = error "renameHsSpliceTy: not an HsSplicedTy" +renameHsSpliceTy _ = error "renameHsSpliceTy: not an HsSpliced" renameLHsQTyVars :: LHsQTyVars GhcRn -> RnM (LHsQTyVars DocNameI) renameLHsQTyVars (HsQTvs { hsq_explicit = tvs }) @@ -644,11 +664,11 @@ renameWc rn_thing (HsWC { hswc_body = thing }) renameWc _ (XHsWildCardBndrs _) = panic "haddock:renameWc" renameDocInstance :: DocInstance GhcRn -> RnM (DocInstance DocNameI) -renameDocInstance (inst, idoc, L l n) = do +renameDocInstance (inst, idoc, L l n, m) = do inst' <- renameInstHead inst n' <- rename n idoc' <- mapM renameDoc idoc - return (inst', idoc',L l n') + return (inst', idoc', L l n', m) renameExportItem :: ExportItem GhcRn -> RnM (ExportItem DocNameI) renameExportItem item = case item of diff --git a/haddock-api/src/Haddock/Interface/Specialize.hs b/haddock-api/src/Haddock/Interface/Specialize.hs index 092a2f4e..2fcb495c 100644 --- a/haddock-api/src/Haddock/Interface/Specialize.hs +++ b/haddock-api/src/Haddock/Interface/Specialize.hs @@ -29,23 +29,23 @@ import qualified Data.Set as Set -- | Instantiate all occurrences of given names with corresponding types. specialize :: Data a => [(Name, HsType GhcRn)] -> a -> a -specialize specs = go +specialize specs = go spec_map0 where - go :: forall x. Data x => x -> x - go = everywhereButType @Name $ mkT $ sugar . strip_kind_sig . specialize_ty_var + go :: forall x. Data x => Map Name (HsType GhcRn) -> x -> x + go spec_map = everywhereButType @Name $ mkT $ sugar . strip_kind_sig . specialize_ty_var spec_map strip_kind_sig :: HsType name -> HsType name strip_kind_sig (HsKindSig _ (L _ t) _) = t strip_kind_sig typ = typ - specialize_ty_var :: HsType GhcRn -> HsType GhcRn - specialize_ty_var (HsTyVar _ _ (L _ name')) + specialize_ty_var :: Map Name (HsType GhcRn) -> HsType GhcRn -> HsType GhcRn + specialize_ty_var spec_map (HsTyVar _ _ (L _ name')) | Just t <- Map.lookup name' spec_map = t - specialize_ty_var typ = typ - -- This is a tricky recursive definition that is guaranteed to terminate - -- because a type binder cannot be instantiated with a type that depends - -- on that binder. i.e. @a -> Maybe a@ is invalid - spec_map = Map.fromList [ (n, go t) | (n, t) <- specs] + specialize_ty_var _ typ = typ + + -- This is a tricky recursive definition. By adding in the specializations + -- one by one, we should avoid infinite loops. + spec_map0 = foldr (\(n,t) acc -> Map.insert n (go acc t) acc) mempty specs -- | Instantiate given binders with corresponding types. diff --git a/haddock-api/src/Haddock/InterfaceFile.hs b/haddock-api/src/Haddock/InterfaceFile.hs index a4e9eb3c..ce6ecc78 100644 --- a/haddock-api/src/Haddock/InterfaceFile.hs +++ b/haddock-api/src/Haddock/InterfaceFile.hs @@ -83,7 +83,7 @@ binaryInterfaceMagic = 0xD0Cface -- binaryInterfaceVersion :: Word16 #if (__GLASGOW_HASKELL__ >= 805) && (__GLASGOW_HASKELL__ < 807) -binaryInterfaceVersion = 32 +binaryInterfaceVersion = 33 binaryInterfaceVersionCompatibility :: [Word16] binaryInterfaceVersionCompatibility = [binaryInterfaceVersion] @@ -459,9 +459,40 @@ instance Binary a => Binary (Header a) where t <- get bh return (Header l t) +instance Binary a => Binary (Table a) where + put_ bh (Table h b) = do + put_ bh h + put_ bh b + get bh = do + h <- get bh + b <- get bh + return (Table h b) + +instance Binary a => Binary (TableRow a) where + put_ bh (TableRow cs) = put_ bh cs + get bh = do + cs <- get bh + return (TableRow cs) + +instance Binary a => Binary (TableCell a) where + put_ bh (TableCell i j c) = do + put_ bh i + put_ bh j + put_ bh c + get bh = do + i <- get bh + j <- get bh + c <- get bh + return (TableCell i j c) + instance Binary Meta where - put_ bh Meta { _version = v } = put_ bh v - get bh = (\v -> Meta { _version = v }) <$> get bh + put_ bh (Meta v p) = do + put_ bh v + put_ bh p + get bh = do + v <- get bh + p <- get bh + return (Meta v p) instance (Binary mod, Binary id) => Binary (MetaDoc mod id) where put_ bh MetaDoc { _meta = m, _doc = d } = do @@ -542,6 +573,9 @@ instance (Binary mod, Binary id) => Binary (DocH mod id) where put_ bh (DocMathDisplay x) = do putByte bh 22 put_ bh x + put_ bh (DocTable x) = do + putByte bh 23 + put_ bh x get bh = do h <- getByte bh @@ -615,6 +649,9 @@ instance (Binary mod, Binary id) => Binary (DocH mod id) where 22 -> do x <- get bh return (DocMathDisplay x) + 23 -> do + x <- get bh + return (DocTable x) _ -> error "invalid binary data found in the interface file" diff --git a/haddock-api/src/Haddock/Options.hs b/haddock-api/src/Haddock/Options.hs index caf1fefe..b5e987d8 100644 --- a/haddock-api/src/Haddock/Options.hs +++ b/haddock-api/src/Haddock/Options.hs @@ -29,19 +29,23 @@ module Haddock.Options ( optLaTeXStyle, optMathjax, qualification, + sinceQualification, verbosity, ghcFlags, reexportFlags, readIfaceArgs, optPackageName, - optPackageVersion + optPackageVersion, + modulePackageInfo ) where import qualified Data.Char as Char import Data.Version +import Control.Applicative import Distribution.Verbosity import FastString +import GHC ( DynFlags, Module, moduleUnitId ) import Haddock.Types import Haddock.Utils import Packages @@ -86,6 +90,8 @@ data Flag | Flag_GenIndex | Flag_IgnoreAllExports | Flag_HideModule String + | Flag_ShowModule String + | Flag_ShowAllModules | Flag_ShowExtensions String | Flag_OptGhc String | Flag_GhcLibDir String @@ -101,6 +107,7 @@ data Flag | Flag_PackageName String | Flag_PackageVersion String | Flag_Reexport String + | Flag_SinceQualification String deriving (Eq, Show) @@ -182,6 +189,10 @@ options backwardsCompat = "behave as if all modules have the\nignore-exports atribute", Option [] ["hide"] (ReqArg Flag_HideModule "MODULE") "behave as if MODULE has the hide attribute", + Option [] ["show"] (ReqArg Flag_ShowModule "MODULE") + "behave as if MODULE does not have the hide attribute", + Option [] ["show-all"] (NoArg Flag_ShowAllModules) + "behave as if not modules have the hide attribute", Option [] ["show-extensions"] (ReqArg Flag_ShowExtensions "MODULE") "behave as if MODULE has the show-extensions attribute", Option [] ["optghc"] (ReqArg Flag_OptGhc "OPTION") @@ -204,7 +215,9 @@ options backwardsCompat = Option [] ["package-name"] (ReqArg Flag_PackageName "NAME") "name of the package being documented", Option [] ["package-version"] (ReqArg Flag_PackageVersion "VERSION") - "version of the package being documented in usual x.y.z.w format" + "version of the package being documented in usual x.y.z.w format", + Option [] ["since-qual"] (ReqArg Flag_SinceQualification "QUAL") + "package qualification of @since, one of\n'always' (default) or 'only-external'" ] @@ -304,6 +317,14 @@ qualification flags = [arg] -> Left $ "unknown qualification type " ++ show arg _:_ -> Left "qualification option given multiple times" +sinceQualification :: [Flag] -> Either String SinceQual +sinceQualification flags = + case map (map Char.toLower) [ str | Flag_SinceQualification str <- flags ] of + [] -> Right Always + ["always"] -> Right Always + ["external"] -> Right External + [arg] -> Left $ "unknown since-qualification type " ++ show arg + _:_ -> Left "since-qualification option given multiple times" verbosity :: [Flag] -> Verbosity verbosity flags = @@ -338,3 +359,23 @@ readIfaceArgs flags = [ parseIfaceOption s | Flag_ReadInterface s <- flags ] optLast :: [a] -> Maybe a optLast [] = Nothing optLast xs = Just (last xs) + + +-- | This function has a potential to return 'Nothing' because package name and +-- versions can no longer reliably be extracted in all cases: if the package is +-- not installed yet then this info is no longer available. +-- +-- The @--package-name@ and @--package-version@ Haddock flags allow the user to +-- specify this information manually and it is returned here if present. +modulePackageInfo :: DynFlags + -> [Flag] -- ^ Haddock flags are checked as they may contain + -- the package name or version provided by the user + -- which we prioritise + -> Module + -> (Maybe PackageName, Maybe Data.Version.Version) +modulePackageInfo dflags flags modu = + ( optPackageName flags <|> fmap packageName pkgDb + , optPackageVersion flags <|> fmap packageVersion pkgDb + ) + where + pkgDb = lookupPackage dflags (moduleUnitId modu) diff --git a/haddock-api/src/Haddock/Parser.hs b/haddock-api/src/Haddock/Parser.hs index 47bf814b..58500f1b 100644 --- a/haddock-api/src/Haddock/Parser.hs +++ b/haddock-api/src/Haddock/Parser.hs @@ -28,8 +28,8 @@ import RdrName (RdrName) import SrcLoc (mkRealSrcLoc, unLoc) import StringBuffer (stringToStringBuffer) -parseParas :: DynFlags -> String -> MetaDoc mod RdrName -parseParas d = overDoc (P.overIdentifier (parseIdent d)) . P.parseParas +parseParas :: DynFlags -> Maybe Package -> String -> MetaDoc mod RdrName +parseParas d p = overDoc (P.overIdentifier (parseIdent d)) . P.parseParas p parseString :: DynFlags -> String -> DocH mod RdrName parseString d = P.overIdentifier (parseIdent d) . P.parseString diff --git a/haddock-api/src/Haddock/Types.hs b/haddock-api/src/Haddock/Types.hs index 8e879cc8..a5ebfa42 100644 --- a/haddock-api/src/Haddock/Types.hs +++ b/haddock-api/src/Haddock/Types.hs @@ -38,8 +38,6 @@ import BasicTypes (Fixity(..)) import GHC hiding (NoLink) import DynFlags (Language) import qualified GHC.LanguageExtensions as LangExt -import Coercion -import NameSet import OccName import Outputable import Control.Applicative (Applicative(..)) @@ -390,7 +388,7 @@ mkPseudoFamilyDecl (XFamilyDecl {}) = panic "haddock:mkPseudoFamilyDecl" -- | An instance head that may have documentation and a source location. -type DocInstance name = (InstHead name, Maybe (MDoc (IdP name)), Located (IdP name)) +type DocInstance name = (InstHead name, Maybe (MDoc (IdP name)), Located (IdP name), Maybe Module) -- | The head of an instance. Consists of a class name, a list of type -- parameters (which may be annotated with kinds), and an instance type @@ -456,6 +454,7 @@ instance (NFData a, NFData mod) DocProperty a -> a `deepseq` () DocExamples a -> a `deepseq` () DocHeader a -> a `deepseq` () + DocTable a -> a `deepseq` () #if !MIN_VERSION_ghc(8,0,2) -- These were added to GHC itself in 8.0.2 @@ -476,6 +475,14 @@ instance NFData Picture where instance NFData Example where rnf (Example a b) = a `deepseq` b `deepseq` () +instance NFData id => NFData (Table id) where + rnf (Table h b) = h `deepseq` b `deepseq` () + +instance NFData id => NFData (TableRow id) where + rnf (TableRow cs) = cs `deepseq` () + +instance NFData id => NFData (TableCell id) where + rnf (TableCell i j c) = i `deepseq` j `deepseq` c `deepseq` () exampleToString :: Example -> String exampleToString (Example expression result) = @@ -571,6 +578,12 @@ data HideEmptyContexts = HideEmptyContexts | ShowEmptyToplevelContexts +-- | When to qualify @since@ annotations with their package +data SinceQual + = Always + | External -- ^ only qualify when the thing being annotated is from + -- an external package + ----------------------------------------------------------------------------- -- * Error handling ----------------------------------------------------------------------------- diff --git a/haddock-api/src/Haddock/Utils.hs b/haddock-api/src/Haddock/Utils.hs index e3cc9655..c2cdddf7 100644 --- a/haddock-api/src/Haddock/Utils.hs +++ b/haddock-api/src/Haddock/Utils.hs @@ -62,7 +62,6 @@ import Haddock.GhcUtils import GHC import Name -import NameSet ( emptyNameSet ) import HsTypes (extFieldOcc) import Outputable ( panic ) diff --git a/haddock-api/test/Haddock/Backends/Hyperlinker/ParserSpec.hs b/haddock-api/test/Haddock/Backends/Hyperlinker/ParserSpec.hs index 8cd2690e..4639253c 100644 --- a/haddock-api/test/Haddock/Backends/Hyperlinker/ParserSpec.hs +++ b/haddock-api/test/Haddock/Backends/Hyperlinker/ParserSpec.hs @@ -4,95 +4,149 @@ module Haddock.Backends.Hyperlinker.ParserSpec (main, spec) where import Test.Hspec import Test.QuickCheck +import qualified GHC +import Control.Monad.IO.Class + +import Haddock (getGhcDirs) import Haddock.Backends.Hyperlinker.Parser import Haddock.Backends.Hyperlinker.Types +withDynFlags :: (GHC.DynFlags -> IO ()) -> IO () +withDynFlags cont = do + libDir <- fmap snd (getGhcDirs []) + GHC.runGhc (Just libDir) $ do + dflags <- GHC.getSessionDynFlags + liftIO $ cont dflags + main :: IO () main = hspec spec spec :: Spec -spec = do - describe "parse" parseSpec +spec = describe "parse" parseSpec -parseSpec :: Spec -parseSpec = do +-- | Defined for its instance of 'Arbitrary'. Represents strings that, when +-- considered as GHC source, won't be rewritten. +newtype NoGhcRewrite = NoGhcRewrite String deriving (Show, Eq) - it "is total" $ - property $ \src -> length (parse src) `shouldSatisfy` (>= 0) +-- | Filter out strings where GHC would replace/remove some characters during +-- lexing. +noGhcRewrite :: String -> Bool +noGhcRewrite ('\t':_) = False -- GHC replaces tabs with 8 spaces +noGhcRewrite ('\r':_) = False +noGhcRewrite ('\f':_) = False +noGhcRewrite ('\v':_) = False +noGhcRewrite (' ':'\n':_) = False -- GHC strips whitespace on empty lines +noGhcRewrite (_:s) = noGhcRewrite s +noGhcRewrite "" = True - it "retains file layout" $ - property $ \src -> concatMap tkValue (parse src) == src +instance Arbitrary NoGhcRewrite where + arbitrary = fmap NoGhcRewrite (arbitrary `suchThat` noGhcRewrite) + shrink (NoGhcRewrite src) = [ NoGhcRewrite shrunk + | shrunk <- shrink src + , noGhcRewrite shrunk + ] - context "when parsing single-line comments" $ do - it "should ignore content until the end of line" $ - "-- some very simple comment\nidentifier" - `shouldParseTo` - [TkComment, TkSpace, TkIdentifier] +parseSpec :: Spec +parseSpec = around withDynFlags $ do - it "should allow endline escaping" $ - "-- first line\\\nsecond line\\\nand another one" - `shouldParseTo` - [TkComment] + it "is total" $ \dflags -> + property $ \src -> length (parse dflags "" src) `shouldSatisfy` (>= 0) - context "when parsing multi-line comments" $ do + it "retains file layout" $ \dflags -> + property $ \(NoGhcRewrite src) -> concatMap tkValue (parse dflags "" src) == src - it "should support nested comments" $ - "{- comment {- nested -} still comment -} {- next comment -}" - `shouldParseTo` - [TkComment, TkSpace, TkComment] + context "when parsing single-line comments" $ do + + it "should ignore content until the end of line" $ \dflags -> + shouldParseTo + "-- some very simple comment\nidentifier" + [TkComment, TkSpace, TkIdentifier] + dflags - it "should distinguish compiler pragma" $ - "{- comment -}{-# LANGUAGE GADTs #-}{- comment -}" - `shouldParseTo` - [TkComment, TkPragma, TkComment] + it "should allow endline escaping" $ \dflags -> + shouldParseTo + "#define first line\\\nsecond line\\\nand another one" + [TkCpp] + dflags - it "should recognize preprocessor directives" $ do - "\n#define foo bar" `shouldParseTo` [TkSpace, TkCpp] - "x # y" `shouldParseTo` - [TkIdentifier, TkSpace, TkOperator, TkSpace,TkIdentifier] + context "when parsing multi-line comments" $ do - it "should distinguish basic language constructs" $ do - "(* 2) <$> (\"abc\", foo)" `shouldParseTo` + it "should support nested comments" $ \dflags -> + shouldParseTo + "{- comment {- nested -} still comment -} {- next comment -}" + [TkComment, TkSpace, TkComment] + dflags + + it "should distinguish compiler pragma" $ \dflags -> + shouldParseTo + "{- comment -}{-# LANGUAGE GADTs #-}{- comment -}" + [TkComment, TkPragma, TkComment] + dflags + + it "should recognize preprocessor directives" $ \dflags -> do + shouldParseTo + "\n#define foo bar" + [TkSpace, TkCpp] + dflags + shouldParseTo + "x # y" + [TkIdentifier, TkSpace, TkOperator, TkSpace,TkIdentifier] + dflags + + it "should distinguish basic language constructs" $ \dflags -> do + + shouldParseTo + "(* 2) <$> (\"abc\", foo)" [ TkSpecial, TkOperator, TkSpace, TkNumber, TkSpecial , TkSpace, TkOperator, TkSpace , TkSpecial, TkString, TkSpecial, TkSpace, TkIdentifier, TkSpecial ] - "let foo' = foo in foo' + foo'" `shouldParseTo` + dflags + + shouldParseTo + "let foo' = foo in foo' + foo'" [ TkKeyword, TkSpace, TkIdentifier , TkSpace, TkGlyph, TkSpace , TkIdentifier, TkSpace, TkKeyword, TkSpace , TkIdentifier, TkSpace, TkOperator, TkSpace, TkIdentifier ] - "square x = y^2 where y = x" `shouldParseTo` + dflags + + shouldParseTo + "square x = y^2 where y = x" [ TkIdentifier, TkSpace, TkIdentifier , TkSpace, TkGlyph, TkSpace , TkIdentifier, TkOperator, TkNumber , TkSpace, TkKeyword, TkSpace , TkIdentifier, TkSpace, TkGlyph, TkSpace, TkIdentifier ] + dflags - it "should parse do-notation syntax" $ do - "do { foo <- getLine; putStrLn foo }" `shouldParseTo` + it "should parse do-notation syntax" $ \dflags -> do + shouldParseTo + "do { foo <- getLine; putStrLn foo }" [ TkKeyword, TkSpace, TkSpecial, TkSpace , TkIdentifier, TkSpace, TkGlyph, TkSpace , TkIdentifier, TkSpecial, TkSpace , TkIdentifier, TkSpace, TkIdentifier, TkSpace, TkSpecial ] - - unlines - [ "do" - , " foo <- getLine" - , " putStrLn foo" - ] `shouldParseTo` + dflags + + shouldParseTo + (unlines + [ "do" + , " foo <- getLine" + , " putStrLn foo" + ]) [ TkKeyword, TkSpace, TkIdentifier , TkSpace, TkGlyph, TkSpace, TkIdentifier, TkSpace , TkIdentifier, TkSpace, TkIdentifier, TkSpace ] - - -shouldParseTo :: String -> [TokenType] -> Expectation -str `shouldParseTo` tokens = map tkType (parse str) `shouldBe` tokens + dflags + where + shouldParseTo :: String -> [TokenType] -> GHC.DynFlags -> Expectation + shouldParseTo str tokens dflags = map tkType (parse dflags "" str) `shouldBe` tokens diff --git a/haddock-library/CHANGES.md b/haddock-library/CHANGES.md index 53d17f5e..e41b8087 100644 --- a/haddock-library/CHANGES.md +++ b/haddock-library/CHANGES.md @@ -1,9 +1,20 @@ -## Changes in version 1.4.6 +## Changes in version 1.6.0 - * to be released + * `MetaDoc` stores package name for since annotations + +## Changes in version 1.5.0.1 + + * Support for parsing unicode operators (#458) + +## Changes in version 1.5.0 * Bifunctor, Bifoldable and Bitraversable instances for DocH and MetaDoc + * Support for grid tables + * added `DocTable` constructor to `DocH` + * added `Table`, `TableCell` and `TableRow` data types + * added `markupTable` to `DocMarkupH` data type + ## Changes in version 1.4.5 * Move markup related data types to haddock-library diff --git a/haddock-library/fixtures/Fixtures.hs b/haddock-library/fixtures/Fixtures.hs new file mode 100644 index 00000000..a4e4321f --- /dev/null +++ b/haddock-library/fixtures/Fixtures.hs @@ -0,0 +1,165 @@ +{-# LANGUAGE DeriveGeneric, StandaloneDeriving #-} +{-# OPTIONS_GHC -fno-warn-orphans #-} +module Main (main) where + +import Control.Applicative ((<|>)) +import Control.Exception (IOException, catch) +import Control.Monad (when) +import Data.Foldable (traverse_) +import Data.List (foldl') +import Data.Traversable (for) +import GHC.Generics (Generic) +import Prelude () +import Prelude.Compat +import System.Directory (getDirectoryContents) +import System.Exit (exitFailure) +import System.FilePath +import System.IO + +import Data.TreeDiff +import Data.TreeDiff.Golden + +import qualified Options.Applicative as O + +import Documentation.Haddock.Types +import qualified Documentation.Haddock.Parser as Parse + +type Doc id = DocH () id + +data Fixture = Fixture + { fixtureName :: FilePath + , fixtureOutput :: FilePath + } + deriving Show + +data Result = Result + { _resultSuccess :: !Int + , _resultTotal :: !Int + } + deriving Show + +combineResults :: Result -> Result -> Result +combineResults (Result s t) (Result s' t') = Result (s + s') (t + t') + +readFixtures :: IO [Fixture] +readFixtures = do + let dir = "fixtures/examples" + files <- getDirectoryContents dir + let inputs = filter (\fp -> takeExtension fp == ".input") files + return $ flip map inputs $ \fp -> Fixture + { fixtureName = dir </> fp + , fixtureOutput = dir </> fp -<.> "parsed" + } + +goldenFixture + :: String + -> IO Expr + -> IO Expr + -> (Expr -> Expr -> IO (Maybe String)) + -> (Expr -> IO ()) + -> IO Result +goldenFixture name expect actual cmp wrt = do + putStrLn $ "running " ++ name + a <- actual + e <- expect `catch` handler a + mres <- cmp e a + case mres of + Nothing -> return (Result 1 1) + Just str -> do + putStrLn str + return (Result 0 1) + where + handler :: Expr -> IOException -> IO Expr + handler a exc = do + putStrLn $ "Caught " ++ show exc + putStrLn "Accepting the test" + wrt a + return a + +runFixtures :: [Fixture] -> IO () +runFixtures fixtures = do + results <- for fixtures $ \(Fixture i o) -> do + let name = takeBaseName i + let readDoc = do + input <- readFile i + return (parseString input) + ediffGolden goldenFixture name o readDoc + case foldl' combineResults (Result 0 0) results of + Result s t -> do + putStrLn $ "Fixtures: success " ++ show s ++ "; total " ++ show t + when (s /= t) exitFailure + +listFixtures :: [Fixture] -> IO () +listFixtures = traverse_ $ \(Fixture i _) -> do + let name = takeBaseName i + putStrLn name + +acceptFixtures :: [Fixture] -> IO () +acceptFixtures = traverse_ $ \(Fixture i o) -> do + input <- readFile i + let doc = parseString input + let actual = show (prettyExpr $ toExpr doc) ++ "\n" + writeFile o actual + +parseString :: String -> Doc String +parseString = Parse.toRegular . _doc . Parse.parseParas Nothing + +data Cmd = CmdRun | CmdAccept | CmdList + +main :: IO () +main = do + hSetBuffering stdout NoBuffering -- For interleaved output when debugging + runCmd =<< O.execParser opts + where + opts = O.info (O.helper <*> cmdParser) O.fullDesc + + cmdParser :: O.Parser Cmd + cmdParser = cmdRun <|> cmdAccept <|> cmdList <|> pure CmdRun + + cmdRun = O.flag' CmdRun $ mconcat + [ O.long "run" + , O.help "Run parser fixtures" + ] + + cmdAccept = O.flag' CmdAccept $ mconcat + [ O.long "accept" + , O.help "Run & accept parser fixtures" + ] + + cmdList = O.flag' CmdList $ mconcat + [ O.long "list" + , O.help "List fixtures" + ] + +runCmd :: Cmd -> IO () +runCmd CmdRun = readFixtures >>= runFixtures +runCmd CmdList = readFixtures >>= listFixtures +runCmd CmdAccept = readFixtures >>= acceptFixtures + +------------------------------------------------------------------------------- +-- Orphans +------------------------------------------------------------------------------- + +deriving instance Generic (DocH mod id) +instance (ToExpr mod, ToExpr id) => ToExpr (DocH mod id) + +deriving instance Generic (Header id) +instance ToExpr id => ToExpr (Header id) + +deriving instance Generic Hyperlink +instance ToExpr Hyperlink + +deriving instance Generic Picture +instance ToExpr Picture + +deriving instance Generic Example +instance ToExpr Example + +deriving instance Generic (Table id) +instance ToExpr id => ToExpr (Table id) + +deriving instance Generic (TableRow id) +instance ToExpr id => ToExpr (TableRow id) + +deriving instance Generic (TableCell id) +instance ToExpr id => ToExpr (TableCell id) diff --git a/haddock-library/fixtures/examples/definitionList.input b/haddock-library/fixtures/examples/definitionList.input new file mode 100644 index 00000000..e1bffb21 --- /dev/null +++ b/haddock-library/fixtures/examples/definitionList.input @@ -0,0 +1 @@ +[foo]: bar diff --git a/haddock-library/fixtures/examples/definitionList.parsed b/haddock-library/fixtures/examples/definitionList.parsed new file mode 100644 index 00000000..048aa141 --- /dev/null +++ b/haddock-library/fixtures/examples/definitionList.parsed @@ -0,0 +1 @@ +DocDefList [_×_ (DocString "foo") (DocString "bar")] diff --git a/haddock-library/fixtures/examples/identifier.input b/haddock-library/fixtures/examples/identifier.input new file mode 100644 index 00000000..c2c4af01 --- /dev/null +++ b/haddock-library/fixtures/examples/identifier.input @@ -0,0 +1 @@ +'foo' diff --git a/haddock-library/fixtures/examples/identifier.parsed b/haddock-library/fixtures/examples/identifier.parsed new file mode 100644 index 00000000..3405a5c9 --- /dev/null +++ b/haddock-library/fixtures/examples/identifier.parsed @@ -0,0 +1 @@ +DocParagraph (DocIdentifier "foo") diff --git a/haddock-library/fixtures/examples/identifierBackticks.input b/haddock-library/fixtures/examples/identifierBackticks.input new file mode 100644 index 00000000..347253a0 --- /dev/null +++ b/haddock-library/fixtures/examples/identifierBackticks.input @@ -0,0 +1 @@ +`foo` diff --git a/haddock-library/fixtures/examples/identifierBackticks.parsed b/haddock-library/fixtures/examples/identifierBackticks.parsed new file mode 100644 index 00000000..3405a5c9 --- /dev/null +++ b/haddock-library/fixtures/examples/identifierBackticks.parsed @@ -0,0 +1 @@ +DocParagraph (DocIdentifier "foo") diff --git a/haddock-library/fixtures/examples/link.input b/haddock-library/fixtures/examples/link.input new file mode 100644 index 00000000..a55c05a6 --- /dev/null +++ b/haddock-library/fixtures/examples/link.input @@ -0,0 +1 @@ +[link](http://example.com) diff --git a/haddock-library/fixtures/examples/link.parsed b/haddock-library/fixtures/examples/link.parsed new file mode 100644 index 00000000..0e85338c --- /dev/null +++ b/haddock-library/fixtures/examples/link.parsed @@ -0,0 +1,5 @@ +DocParagraph + (DocHyperlink + Hyperlink + {hyperlinkLabel = Just "link", + hyperlinkUrl = "http://example.com"}) diff --git a/haddock-library/fixtures/examples/linkInline.input b/haddock-library/fixtures/examples/linkInline.input new file mode 100644 index 00000000..eeca5a07 --- /dev/null +++ b/haddock-library/fixtures/examples/linkInline.input @@ -0,0 +1 @@ +Bla [link](http://example.com) diff --git a/haddock-library/fixtures/examples/linkInline.parsed b/haddock-library/fixtures/examples/linkInline.parsed new file mode 100644 index 00000000..43470d7b --- /dev/null +++ b/haddock-library/fixtures/examples/linkInline.parsed @@ -0,0 +1,6 @@ +DocParagraph + (DocAppend + (DocString "Bla ") + (DocHyperlink + Hyperlink + {hyperlinkLabel = Just "link", hyperlinkUrl = "http://example.com"})) diff --git a/haddock-library/fixtures/examples/table-simple.input b/haddock-library/fixtures/examples/table-simple.input new file mode 100644 index 00000000..d9c49f87 --- /dev/null +++ b/haddock-library/fixtures/examples/table-simple.input @@ -0,0 +1,7 @@ ++------+--------------+------------------------------------------+ +| code | message | description | ++======+==============+==========================================+ +| 200 | @OK@ | operation successful | ++------+--------------+------------------------------------------+ +| 204 | @No Content@ | operation successful, no body returned | ++------+--------------+------------------------------------------+ diff --git a/haddock-library/fixtures/examples/table-simple.parsed b/haddock-library/fixtures/examples/table-simple.parsed new file mode 100644 index 00000000..b5e62453 --- /dev/null +++ b/haddock-library/fixtures/examples/table-simple.parsed @@ -0,0 +1,52 @@ +DocTable + Table + {tableBodyRows = [TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " 200 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocAppend + (DocString " ") + (DocAppend + (DocMonospaced (DocString "OK")) + (DocString " ")), + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString + " operation successful ", + tableCellRowspan = 1}], + TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " 204 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocAppend + (DocString " ") + (DocAppend + (DocMonospaced (DocString "No Content")) + (DocString " ")), + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString + " operation successful, no body returned ", + tableCellRowspan = 1}]], + tableHeaderRows = [TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " code ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " message ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString + " description ", + tableCellRowspan = 1}]]} diff --git a/haddock-library/fixtures/examples/table1.input b/haddock-library/fixtures/examples/table1.input new file mode 100644 index 00000000..a007020c --- /dev/null +++ b/haddock-library/fixtures/examples/table1.input @@ -0,0 +1,12 @@ ++------------------------+------------+----------+----------+ +| Header row, column 1 | Header 2 | Header 3 | Header 4 | +| (header rows optional) | | | | ++========================+============+==========+==========+ +| body row 1, column 1 | column 2 | column 3 | column 4 | ++------------------------+------------+----------+----------+ +| body row 2 | Cells may span columns. | ++------------------------+------------+---------------------+ +| body row 3 | Cells may | \[ | ++------------------------+ span rows. | f(n) = \sum_{i=1} | +| body row 4 | | \] | ++------------------------+------------+---------------------+ diff --git a/haddock-library/fixtures/examples/table1.parsed b/haddock-library/fixtures/examples/table1.parsed new file mode 100644 index 00000000..2fa58fd8 --- /dev/null +++ b/haddock-library/fixtures/examples/table1.parsed @@ -0,0 +1,81 @@ +DocTable + Table + {tableBodyRows = [TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " body row 1, column 1 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 2 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 3 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 4 ", + tableCellRowspan = 1}], + TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " body row 2 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 3, + tableCellContents = DocString " Cells may span columns. ", + tableCellRowspan = 1}], + TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " body row 3 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString + (concat + [" Cells may \n", + " span rows. \n", + " "]), + tableCellRowspan = 2}, + TableCell + {tableCellColspan = 2, + tableCellContents = DocAppend + (DocString " ") + (DocAppend + (DocMathDisplay + (concat + [" \n", + " f(n) = \\sum_{i=1} \n", + " "])) + (DocString " ")), + tableCellRowspan = 2}], + TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " body row 4 ", + tableCellRowspan = 1}]], + tableHeaderRows = [TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString + (concat + [" Header row, column 1 \n", + " (header rows optional) "]), + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString + (concat [" Header 2 \n", " "]), + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString + (concat [" Header 3 \n", " "]), + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString + (concat [" Header 4 \n", " "]), + tableCellRowspan = 1}]]} diff --git a/haddock-library/fixtures/examples/table2.input b/haddock-library/fixtures/examples/table2.input new file mode 100644 index 00000000..aa5d0862 --- /dev/null +++ b/haddock-library/fixtures/examples/table2.input @@ -0,0 +1,7 @@ ++--------------+----------+-----------+-----------+ +| row 1, col 1 | column 2 | column 3 | column 4 | ++--------------+----------+-----------+-----------+ +| row 2 | | ++--------------+----------+-----------+-----------+ +| row 3 | | | | ++--------------+----------+-----------+-----------+ diff --git a/haddock-library/fixtures/examples/table2.parsed b/haddock-library/fixtures/examples/table2.parsed new file mode 100644 index 00000000..e3dbf0b4 --- /dev/null +++ b/haddock-library/fixtures/examples/table2.parsed @@ -0,0 +1,46 @@ +DocTable + Table + {tableBodyRows = [TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " row 1, col 1 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 2 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 3 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 4 ", + tableCellRowspan = 1}], + TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " row 2 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 3, + tableCellContents = DocString " ", + tableCellRowspan = 1}], + TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " row 3 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " ", + tableCellRowspan = 1}]], + tableHeaderRows = []} diff --git a/haddock-library/fixtures/examples/table3.input b/haddock-library/fixtures/examples/table3.input new file mode 100644 index 00000000..a6ca84ca --- /dev/null +++ b/haddock-library/fixtures/examples/table3.input @@ -0,0 +1,7 @@ ++--------------+----------+-----------+-----------+ +| row 1, col 1 | column 2 | column 3 | column 4 | ++--------------+----------+-----------+-----------+ +| row 2 | Use the command ``ls | more``. | ++--------------+----------+-----------+-----------+ +| row 3 | | | | ++--------------+----------+-----------+-----------+ diff --git a/haddock-library/fixtures/examples/table3.parsed b/haddock-library/fixtures/examples/table3.parsed new file mode 100644 index 00000000..cabff9cb --- /dev/null +++ b/haddock-library/fixtures/examples/table3.parsed @@ -0,0 +1,50 @@ +DocTable + Table + {tableBodyRows = [TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " row 1, col 1 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 2 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 3 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 4 ", + tableCellRowspan = 1}], + TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " row 2 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 2, + tableCellContents = DocString " Use the command ``ls ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " more``. ", + tableCellRowspan = 1}], + TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " row 3 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " ", + tableCellRowspan = 1}]], + tableHeaderRows = []} diff --git a/haddock-library/fixtures/examples/table4.input b/haddock-library/fixtures/examples/table4.input new file mode 100644 index 00000000..2c5611c8 --- /dev/null +++ b/haddock-library/fixtures/examples/table4.input @@ -0,0 +1,17 @@ +Single outer cell: + ++-------------+ +| outer | +| | ++-------+ | +| inner | | ++-------+-----+ + +Broken (only inner cell is rendered): + ++-------+-----+ +| inner | | ++-------+ | +| | +| outer | ++-------------+ diff --git a/haddock-library/fixtures/examples/table4.parsed b/haddock-library/fixtures/examples/table4.parsed new file mode 100644 index 00000000..cfdd6f0f --- /dev/null +++ b/haddock-library/fixtures/examples/table4.parsed @@ -0,0 +1,26 @@ +DocAppend + (DocParagraph (DocString "Single outer cell:")) + (DocAppend + (DocTable + Table + {tableBodyRows = [TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString + (concat + [" outer \n", + " \n", + "-------+ \n", + " inner | "]), + tableCellRowspan = 1}]], + tableHeaderRows = []}) + (DocAppend + (DocParagraph (DocString "Broken (only inner cell is rendered):")) + (DocTable + Table + {tableBodyRows = [TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " inner ", + tableCellRowspan = 1}]], + tableHeaderRows = []}))) diff --git a/haddock-library/fixtures/examples/table5.input b/haddock-library/fixtures/examples/table5.input new file mode 100644 index 00000000..7cf26512 --- /dev/null +++ b/haddock-library/fixtures/examples/table5.input @@ -0,0 +1,8 @@ ++--------------+----------+-----------+-----------+ +| row 1, col 1 | column 2 | column 3 | column 4 | ++==============+==========+===========+===========+ +| row 2 | Use the command @ls | more@. | +| | | +| +----------+-----------+-----------+ +| row 3 | | | | ++--------------+----------+-----------+-----------+ diff --git a/haddock-library/fixtures/examples/table5.parsed b/haddock-library/fixtures/examples/table5.parsed new file mode 100644 index 00000000..9a547ad3 --- /dev/null +++ b/haddock-library/fixtures/examples/table5.parsed @@ -0,0 +1,53 @@ +DocTable + Table + {tableBodyRows = [TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString + (concat + [" row 2 \n", + " \n", + " \n", + " row 3 "]), + tableCellRowspan = 2}, + TableCell + {tableCellColspan = 3, + tableCellContents = DocAppend + (DocString " Use the command ") + (DocAppend + (DocMonospaced (DocString "ls | more")) + (DocString + (concat + [". \n", + " "]))), + tableCellRowspan = 1}], + TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " ", + tableCellRowspan = 1}]], + tableHeaderRows = [TableRow + [TableCell + {tableCellColspan = 1, + tableCellContents = DocString " row 1, col 1 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 2 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 3 ", + tableCellRowspan = 1}, + TableCell + {tableCellColspan = 1, + tableCellContents = DocString " column 4 ", + tableCellRowspan = 1}]]} diff --git a/haddock-library/fixtures/examples/url.input b/haddock-library/fixtures/examples/url.input new file mode 100644 index 00000000..5bfed0a1 --- /dev/null +++ b/haddock-library/fixtures/examples/url.input @@ -0,0 +1 @@ +<http://example.com/> diff --git a/haddock-library/fixtures/examples/url.parsed b/haddock-library/fixtures/examples/url.parsed new file mode 100644 index 00000000..0fbbbb30 --- /dev/null +++ b/haddock-library/fixtures/examples/url.parsed @@ -0,0 +1,4 @@ +DocParagraph + (DocHyperlink + Hyperlink + {hyperlinkLabel = Nothing, hyperlinkUrl = "http://example.com/"}) diff --git a/haddock-library/fixtures/examples/urlLabel.input b/haddock-library/fixtures/examples/urlLabel.input new file mode 100644 index 00000000..729812e8 --- /dev/null +++ b/haddock-library/fixtures/examples/urlLabel.input @@ -0,0 +1 @@ +<http://example.com/ some link> diff --git a/haddock-library/fixtures/examples/urlLabel.parsed b/haddock-library/fixtures/examples/urlLabel.parsed new file mode 100644 index 00000000..d7e3a76c --- /dev/null +++ b/haddock-library/fixtures/examples/urlLabel.parsed @@ -0,0 +1,5 @@ +DocParagraph + (DocHyperlink + Hyperlink + {hyperlinkLabel = Just "some link", + hyperlinkUrl = "http://example.com/"}) diff --git a/haddock-library/haddock-library.cabal b/haddock-library/haddock-library.cabal index 535cff0e..df2dbf93 100644 --- a/haddock-library/haddock-library.cabal +++ b/haddock-library/haddock-library.cabal @@ -1,5 +1,6 @@ +cabal-version: 2.0 name: haddock-library -version: 1.4.6 +version: 1.6.0 synopsis: Library exposing some functionality of Haddock. description: Haddock is a documentation-generation tool for Haskell libraries. These modules expose some functionality of it @@ -8,28 +9,27 @@ description: Haddock is a documentation-generation tool for Haskell project if you can't release often. For interacting with Haddock itself, see the ‘haddock’ package. license: BSD3 -license-file: LICENSE +license-files: LICENSE maintainer: Alex Biehl <alexbiehl@gmail.com>, Simon Hengel <sol@typeful.net>, Mateusz Kowalczyk <fuuzetsu@fuuzetsu.co.uk> homepage: http://www.haskell.org/haddock/ bug-reports: https://github.com/haskell/haddock/issues category: Documentation build-type: Simple -cabal-version: >= 2.0 extra-source-files: CHANGES.md + library default-language: Haskell2010 build-depends: base >= 4.5 && < 4.13 , bytestring >= 0.9.2.1 && < 0.11 + , containers >= 0.4.2.1 && < 0.6 , transformers >= 0.3.0 && < 0.6 - - -- internal sub-lib - build-depends: attoparsec + , text >= 1.2.3.0 && < 1.3 + , parsec >= 3.1.13.0 && < 3.2 hs-source-dirs: src - ghc-options: -funbox-strict-fields -Wall -fwarn-tabs -O2 exposed-modules: Documentation.Haddock.Doc @@ -42,44 +42,9 @@ library other-modules: Documentation.Haddock.Parser.Util - ghc-options: -Wall - if impl(ghc >= 8.0) - ghc-options: -Wcompat -Wnoncanonical-monad-instances -Wnoncanonical-monadfail-instances - -library attoparsec - default-language: Haskell2010 - - build-depends: - base >= 4.5 && < 4.13 - , bytestring >= 0.9.2.1 && < 0.11 - , deepseq >= 1.3 && < 1.5 - - hs-source-dirs: vendor/attoparsec-0.13.1.0 - - -- NB: haddock-library needs only small part of lib:attoparsec - -- internally, so we only bundle that subset here - exposed-modules: - Data.Attoparsec.ByteString - Data.Attoparsec.ByteString.Char8 - - other-modules: - Data.Attoparsec - Data.Attoparsec.ByteString.Buffer - Data.Attoparsec.ByteString.FastSet - Data.Attoparsec.ByteString.Internal - Data.Attoparsec.Combinator - Data.Attoparsec.Internal - Data.Attoparsec.Internal.Fhthagn - Data.Attoparsec.Internal.Types - Data.Attoparsec.Number - - ghc-options: -funbox-strict-fields -Wall -fwarn-tabs -O2 - - ghc-options: -Wall + ghc-options: -funbox-strict-fields -Wall -fwarn-tabs -O2 if impl(ghc >= 8.0) ghc-options: -Wcompat -Wnoncanonical-monad-instances -Wnoncanonical-monadfail-instances - else - build-depends: semigroups ^>= 0.18.3, fail ^>= 4.9.0.0 test-suite spec @@ -106,23 +71,37 @@ test-suite spec Documentation.Haddock.Utf8Spec build-depends: - base-compat ^>= 0.9.3 + base >= 4.5 && < 4.12 + , base-compat >= 0.9.3 && < 0.11 + , bytestring >= 0.9.2.1 && < 0.11 + , containers >= 0.4.2.1 && < 0.6 , transformers >= 0.3.0 && < 0.6 - , hspec ^>= 2.4.4 - , QuickCheck ^>= 2.10 + , hspec >= 2.4.4 && < 2.6 + , QuickCheck ^>= 2.11 + , text >= 1.2.3.0 && < 1.3 + , parsec >= 3.1.13.0 && < 3.2 + , deepseq >= 1.3 && < 1.5 - -- internal sub-lib - build-depends: attoparsec + build-tool-depends: + hspec-discover:hspec-discover >= 2.4.4 && < 2.6 - -- Versions for the dependencies below are transitively pinned by - -- dependency on haddock-library:lib:attoparsec +test-suite fixtures + type: exitcode-stdio-1.0 + default-language: Haskell2010 + main-is: Fixtures.hs + ghc-options: -Wall -O0 + hs-source-dirs: fixtures build-depends: - base - , bytestring - , deepseq - - build-tool-depends: - hspec-discover:hspec-discover ^>= 2.4.4 + base >= 4.5 && < 4.12 + , base-compat >= 0.9.3 && < 0.11 + , directory ^>= 1.3.0.2 + , filepath ^>= 1.4.1.2 + , optparse-applicative ^>= 0.14.0.0 + , tree-diff ^>= 0.0.0.1 + + -- Depend on the library. + build-depends: + haddock-library source-repository head type: git diff --git a/haddock-library/src/Documentation/Haddock/Doc.hs b/haddock-library/src/Documentation/Haddock/Doc.hs index 66bd1c97..297d30d6 100644 --- a/haddock-library/src/Documentation/Haddock/Doc.hs +++ b/haddock-library/src/Documentation/Haddock/Doc.hs @@ -27,16 +27,16 @@ metaDocAppend (MetaDoc { _meta = m, _doc = d }) (MetaDoc { _meta = m', _doc = d' }) = MetaDoc { _meta = m' `metaAppend` m, _doc = d `docAppend` d' } --- | This is not a monoidal append, it uses '<|>' for the '_version'. +-- | This is not a monoidal append, it uses '<|>' for the '_version' and +-- '_package'. metaAppend :: Meta -> Meta -> Meta -metaAppend (Meta { _version = v }) (Meta { _version = v' }) = - Meta { _version = v <|> v' } +metaAppend (Meta v1 p1) (Meta v2 p2) = Meta (v1 <|> v2) (p1 <|> p2) emptyMetaDoc :: MetaDoc mod id emptyMetaDoc = MetaDoc { _meta = emptyMeta, _doc = DocEmpty } emptyMeta :: Meta -emptyMeta = Meta { _version = empty } +emptyMeta = Meta empty empty docAppend :: DocH mod id -> DocH mod id -> DocH mod id docAppend (DocDefList ds1) (DocDefList ds2) = DocDefList (ds1++ds2) diff --git a/haddock-library/src/Documentation/Haddock/Markup.hs b/haddock-library/src/Documentation/Haddock/Markup.hs index 1bf6c084..da8edcd4 100644 --- a/haddock-library/src/Documentation/Haddock/Markup.hs +++ b/haddock-library/src/Documentation/Haddock/Markup.hs @@ -30,6 +30,7 @@ markup m (DocMathDisplay mathjax) = markupMathDisplay m mathjax markup m (DocProperty p) = markupProperty m p markup m (DocExamples e) = markupExample m e markup m (DocHeader (Header l t)) = markupHeader m (Header l (markup m t)) +markup m (DocTable (Table h b)) = markupTable m (Table (map (fmap (markup m)) h) (map (fmap (markup m)) b)) markupPair :: DocMarkupH mod id a -> (DocH mod id, DocH mod id) -> (a, a) markupPair m (a,b) = (markup m a, markup m b) @@ -59,5 +60,6 @@ idMarkup = Markup { markupMathDisplay = DocMathDisplay, markupProperty = DocProperty, markupExample = DocExamples, - markupHeader = DocHeader + markupHeader = DocHeader, + markupTable = DocTable } diff --git a/haddock-library/src/Documentation/Haddock/Parser.hs b/haddock-library/src/Documentation/Haddock/Parser.hs index 8dc2a801..d79da40b 100644 --- a/haddock-library/src/Documentation/Haddock/Parser.hs +++ b/haddock-library/src/Documentation/Haddock/Parser.hs @@ -1,5 +1,6 @@ +{-# LANGUAGE CPP #-} {-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE ViewPatterns #-} +{-# LANGUAGE ViewPatterns #-} -- | -- Module : Documentation.Haddock.Parser -- Copyright : (c) Mateusz Kowalczyk 2013-2014, @@ -15,28 +16,63 @@ -- to be -- -- @'toRegular' . '_doc' . 'parseParas'@ -module Documentation.Haddock.Parser ( parseString, parseParas - , overIdentifier, toRegular, Identifier - ) where +module Documentation.Haddock.Parser ( + parseString, + parseParas, + overIdentifier, + toRegular, + Identifier +) where import Control.Applicative import Control.Arrow (first) import Control.Monad -import qualified Data.ByteString.Char8 as BS -import Data.Char (chr, isAsciiUpper) -import Data.List (stripPrefix, intercalate, unfoldr) -import Data.Maybe (fromMaybe) +import Data.Char (chr, isUpper, isAlpha, isAlphaNum, isSpace) +import Data.List (intercalate, unfoldr, elemIndex, notElem) +import Data.Maybe (fromMaybe, mapMaybe) import Data.Monoid +import qualified Data.Set as Set import Documentation.Haddock.Doc -import Documentation.Haddock.Parser.Monad hiding (take, endOfLine) +import Documentation.Haddock.Parser.Monad import Documentation.Haddock.Parser.Util import Documentation.Haddock.Types -import Documentation.Haddock.Utf8 import Prelude hiding (takeWhile) +import qualified Prelude as P + +import qualified Text.Parsec as Parsec +import Text.Parsec (try) + +import qualified Data.Text as T +import Data.Text (Text) + +#if MIN_VERSION_base(4,9,0) +import Text.Read.Lex (isSymbolChar) +#else +import Data.Char (GeneralCategory (..), + generalCategory) +#endif -- $setup -- >>> :set -XOverloadedStrings +#if !MIN_VERSION_base(4,9,0) +-- inlined from base-4.10.0.0 +isSymbolChar :: Char -> Bool +isSymbolChar c = not (isPuncChar c) && case generalCategory c of + MathSymbol -> True + CurrencySymbol -> True + ModifierSymbol -> True + OtherSymbol -> True + DashPunctuation -> True + OtherPunctuation -> c `notElem` ("'\"" :: String) + ConnectorPunctuation -> c /= '_' + _ -> False + where + -- | The @special@ character class as defined in the Haskell Report. + isPuncChar :: Char -> Bool + isPuncChar = (`elem` (",;()[]{}`" :: String)) +#endif + -- | Identifier string surrounded with opening and closing quotes/backticks. type Identifier = (Char, String, Char) @@ -79,47 +115,72 @@ overIdentifier f d = g d g (DocProperty x) = DocProperty x g (DocExamples x) = DocExamples x g (DocHeader (Header l x)) = DocHeader . Header l $ g x + g (DocTable (Table h b)) = DocTable (Table (map (fmap g) h) (map (fmap g) b)) + -parse :: Parser a -> BS.ByteString -> (ParserState, a) -parse p = either err id . parseOnly (p <* endOfInput) +choice' :: [Parser a] -> Parser a +choice' [] = empty +choice' [p] = p +choice' (p : ps) = try p <|> choice' ps + +parse :: Parser a -> Text -> (ParserState, a) +parse p = either err id . parseOnly (p <* Parsec.eof) where err = error . ("Haddock.Parser.parse: " ++) -- | Main entry point to the parser. Appends the newline character -- to the input string. -parseParas :: String -- ^ String to parse +parseParas :: Maybe Package + -> String -- ^ String to parse -> MetaDoc mod Identifier -parseParas input = case parseParasState input of - (state, a) -> MetaDoc { _meta = Meta { _version = parserStateSince state } +parseParas pkg input = case parseParasState input of + (state, a) -> MetaDoc { _meta = Meta { _version = parserStateSince state + , _package = pkg + } , _doc = a } parseParasState :: String -> (ParserState, DocH mod Identifier) -parseParasState = - parse (p <* skipSpace) . encodeUtf8 . (++ "\n") . filter (/= '\r') +parseParasState = parse (emptyLines *> p) . T.pack . (++ "\n") . filter (/= '\r') where p :: Parser (DocH mod Identifier) - p = docConcat <$> paragraph `sepBy` many (skipHorizontalSpace *> "\n") + p = docConcat <$> many (paragraph <* emptyLines) + + emptyLines :: Parser () + emptyLines = void $ many (try (skipHorizontalSpace *> "\n")) parseParagraphs :: String -> Parser (DocH mod Identifier) parseParagraphs input = case parseParasState input of - (state, a) -> setParserState state >> return a + (state, a) -> Parsec.putState state *> pure a --- | Parse a text paragraph. Actually just a wrapper over 'parseStringBS' which --- drops leading whitespace and encodes the string to UTF8 first. +-- | Variant of 'parseText' for 'String' instead of 'Text' parseString :: String -> DocH mod Identifier -parseString = parseStringBS . encodeUtf8 . dropWhile isSpace . filter (/= '\r') +parseString = parseText . T.pack + +-- | Parse a text paragraph. Actually just a wrapper over 'parseParagraph' which +-- drops leading whitespace. +parseText :: Text -> DocH mod Identifier +parseText = parseParagraph . T.dropWhile isSpace . T.filter (/= '\r') -parseStringBS :: BS.ByteString -> DocH mod Identifier -parseStringBS = snd . parse p +parseParagraph :: Text -> DocH mod Identifier +parseParagraph = snd . parse p where p :: Parser (DocH mod Identifier) - p = docConcat <$> many (monospace <|> anchor <|> identifier <|> moduleName - <|> picture <|> mathDisplay <|> mathInline - <|> markdownImage - <|> hyperlink <|> bold - <|> emphasis <|> encodedChar <|> string' - <|> skipSpecialChar) + p = docConcat <$> many (choice' [ monospace + , anchor + , identifier + , moduleName + , picture + , mathDisplay + , mathInline + , markdownImage + , hyperlink + , bold + , emphasis + , encodedChar + , string' + , skipSpecialChar + ]) -- | Parses and processes -- <https://en.wikipedia.org/wiki/Numeric_character_reference Numeric character references> @@ -143,7 +204,7 @@ specialChar = "_/<@\"&'`# " -- to ensure that we have already given a chance to more meaningful parsers -- before capturing their characers. string' :: Parser (DocH mod a) -string' = DocString . unescape . decodeUtf8 <$> takeWhile1_ (notInClass specialChar) +string' = DocString . unescape . T.unpack <$> takeWhile1_ (`notElem` specialChar) where unescape "" = "" unescape ('\\':x:xs) = x : unescape xs @@ -153,45 +214,45 @@ string' = DocString . unescape . decodeUtf8 <$> takeWhile1_ (notInClass specialC -- This is done to skip over any special characters belonging to other -- elements but which were not deemed meaningful at their positions. skipSpecialChar :: Parser (DocH mod a) -skipSpecialChar = DocString . return <$> satisfy (inClass specialChar) +skipSpecialChar = DocString . return <$> Parsec.oneOf specialChar -- | Emphasis parser. -- -- >>> parseString "/Hello world/" -- DocEmphasis (DocString "Hello world") emphasis :: Parser (DocH mod Identifier) -emphasis = DocEmphasis . parseStringBS <$> - mfilter ('\n' `BS.notElem`) ("/" *> takeWhile1_ (/= '/') <* "/") +emphasis = DocEmphasis . parseParagraph <$> + disallowNewline ("/" *> takeWhile1_ (/= '/') <* "/") -- | Bold parser. -- -- >>> parseString "__Hello world__" -- DocBold (DocString "Hello world") bold :: Parser (DocH mod Identifier) -bold = DocBold . parseStringBS <$> disallowNewline ("__" *> takeUntil "__") +bold = DocBold . parseParagraph <$> disallowNewline ("__" *> takeUntil "__") -disallowNewline :: Parser BS.ByteString -> Parser BS.ByteString -disallowNewline = mfilter ('\n' `BS.notElem`) +disallowNewline :: Parser Text -> Parser Text +disallowNewline = mfilter (T.all (/= '\n')) -- | Like `takeWhile`, but unconditionally take escaped characters. -takeWhile_ :: (Char -> Bool) -> Parser BS.ByteString -takeWhile_ p = scan False p_ +takeWhile_ :: (Char -> Bool) -> Parser Text +takeWhile_ p = scan p_ False where p_ escaped c | escaped = Just False | not $ p c = Nothing | otherwise = Just (c == '\\') --- | Like `takeWhile1`, but unconditionally take escaped characters. -takeWhile1_ :: (Char -> Bool) -> Parser BS.ByteString -takeWhile1_ = mfilter (not . BS.null) . takeWhile_ +-- | Like 'takeWhile1', but unconditionally take escaped characters. +takeWhile1_ :: (Char -> Bool) -> Parser Text +takeWhile1_ = mfilter (not . T.null) . takeWhile_ -- | Text anchors to allow for jumping around the generated documentation. -- -- >>> parseString "#Hello world#" -- DocAName "Hello world" anchor :: Parser (DocH mod a) -anchor = DocAName . decodeUtf8 <$> +anchor = DocAName . T.unpack <$> disallowNewline ("#" *> takeWhile1_ (/= '#') <* "#") -- | Monospaced strings. @@ -199,23 +260,22 @@ anchor = DocAName . decodeUtf8 <$> -- >>> parseString "@cruel@" -- DocMonospaced (DocString "cruel") monospace :: Parser (DocH mod Identifier) -monospace = DocMonospaced . parseStringBS +monospace = DocMonospaced . parseParagraph <$> ("@" *> takeWhile1_ (/= '@') <* "@") --- | Module names: we try our reasonable best to only allow valid --- Haskell module names, with caveat about not matching on technically --- valid unicode symbols. +-- | Module names. +-- +-- Note that we allow '#' and '\' to support anchors (old style anchors are of +-- the form "SomeModule\#anchor"). moduleName :: Parser (DocH mod a) -moduleName = DocModule <$> (char '"' *> modid <* char '"') +moduleName = DocModule <$> ("\"" *> modid <* "\"") where - modid = intercalate "." <$> conid `sepBy1` "." + modid = intercalate "." <$> conid `Parsec.sepBy1` "." conid = (:) - <$> satisfy isAsciiUpper - -- NOTE: According to Haskell 2010 we should actually only - -- accept {small | large | digit | ' } here. But as we can't - -- match on unicode characters, this is currently not possible. - -- Note that we allow ‘#’ to suport anchors. - <*> (decodeUtf8 <$> takeWhile (notInClass " .&[{}(=*)+]!|@/;,^?\"\n")) + <$> Parsec.satisfy (\c -> isAlpha c && isUpper c) + <*> many (conChar <|> Parsec.oneOf "\\#") + + conChar = Parsec.alphaNum <|> Parsec.char '_' -- | Picture parser, surrounded by \<\< and \>\>. It's possible to specify -- a title for the picture. @@ -225,7 +285,7 @@ moduleName = DocModule <$> (char '"' *> modid <* char '"') -- >>> parseString "<<hello.png world>>" -- DocPic (Picture {pictureUri = "hello.png", pictureTitle = Just "world"}) picture :: Parser (DocH mod a) -picture = DocPic . makeLabeled Picture . decodeUtf8 +picture = DocPic . makeLabeled Picture <$> disallowNewline ("<<" *> takeUntil ">>") -- | Inline math parser, surrounded by \\( and \\). @@ -233,7 +293,7 @@ picture = DocPic . makeLabeled Picture . decodeUtf8 -- >>> parseString "\\(\\int_{-\\infty}^{\\infty} e^{-x^2/2} = \\sqrt{2\\pi}\\)" -- DocMathInline "\\int_{-\\infty}^{\\infty} e^{-x^2/2} = \\sqrt{2\\pi}" mathInline :: Parser (DocH mod a) -mathInline = DocMathInline . decodeUtf8 +mathInline = DocMathInline . T.unpack <$> disallowNewline ("\\(" *> takeUntil "\\)") -- | Display math parser, surrounded by \\[ and \\]. @@ -241,7 +301,7 @@ mathInline = DocMathInline . decodeUtf8 -- >>> parseString "\\[\\int_{-\\infty}^{\\infty} e^{-x^2/2} = \\sqrt{2\\pi}\\]" -- DocMathDisplay "\\int_{-\\infty}^{\\infty} e^{-x^2/2} = \\sqrt{2\\pi}" mathDisplay :: Parser (DocH mod a) -mathDisplay = DocMathDisplay . decodeUtf8 +mathDisplay = DocMathDisplay . T.unpack <$> ("\\[" *> takeUntil "\\]") markdownImage :: Parser (DocH mod a) @@ -251,25 +311,213 @@ markdownImage = fromHyperlink <$> ("!" *> linkParser) -- | Paragraph parser, called by 'parseParas'. paragraph :: Parser (DocH mod Identifier) -paragraph = examples <|> do - indent <- takeIndent - choice - [ since - , unorderedList indent - , orderedList indent - , birdtracks - , codeblock - , property - , header - , textParagraphThatStartsWithMarkdownLink - , definitionList indent - , docParagraph <$> textParagraph - ] +paragraph = choice' [ examples + , table + , do indent <- takeIndent + choice' [ since + , unorderedList indent + , orderedList indent + , birdtracks + , codeblock + , property + , header + , textParagraphThatStartsWithMarkdownLink + , definitionList indent + , docParagraph <$> textParagraph + ] + ] + +-- | Provides support for grid tables. +-- +-- Tables are composed by an optional header and body. The header is composed by +-- a single row. The body is composed by a non-empty list of rows. +-- +-- Example table with header: +-- +-- > +----------+----------+ +-- > | /32bit/ | 64bit | +-- > +==========+==========+ +-- > | 0x0000 | @0x0000@ | +-- > +----------+----------+ +-- +-- Algorithms loosely follows ideas in +-- http://docutils.sourceforge.net/docutils/parsers/rst/tableparser.py +-- +table :: Parser (DocH mod Identifier) +table = do + -- first we parse the first row, which determines the width of the table + firstRow <- parseFirstRow + let len = T.length firstRow + + -- then we parse all consequtive rows starting and ending with + or |, + -- of the width `len`. + restRows <- many (try (parseRestRows len)) + + -- Now we gathered the table block, the next step is to split the block + -- into cells. + DocTable <$> tableStepTwo len (firstRow : restRows) + where + parseFirstRow :: Parser Text + parseFirstRow = do + skipHorizontalSpace + -- upper-left corner is + + c <- Parsec.char '+' + cs <- some (Parsec.char '-' <|> Parsec.char '+') + + -- upper right corner is + too + guard (last cs == '+') + + -- trailing space + skipHorizontalSpace + _ <- Parsec.newline + + return (T.cons c $ T.pack cs) + + parseRestRows :: Int -> Parser Text + parseRestRows l = do + skipHorizontalSpace + c <- Parsec.char '|' <|> Parsec.char '+' + bs <- scan predicate (l - 2) + c2 <- Parsec.char '|' <|> Parsec.char '+' + + -- trailing space + skipHorizontalSpace + _ <- Parsec.newline + + return (T.cons c (T.snoc bs c2)) + where + predicate n c + | n <= 0 = Nothing + | c == '\n' = Nothing + | otherwise = Just (n - 1) + +-- Second step searchs for row of '+' and '=' characters, records it's index +-- and changes to '=' to '-'. +tableStepTwo + :: Int -- ^ width + -> [Text] -- ^ rows + -> Parser (Table (DocH mod Identifier)) +tableStepTwo width = go 0 [] where + go _ left [] = tableStepThree width (reverse left) Nothing + go n left (r : rs) + | T.all (`elem` ['+', '=']) r = + tableStepThree width (reverse left ++ r' : rs) (Just n) + | otherwise = + go (n + 1) (r : left) rs + where + r' = T.map (\c -> if c == '=' then '-' else c) r + +-- Third step recognises cells in the table area, returning a list of TC, cells. +tableStepThree + :: Int -- ^ width + -> [Text] -- ^ rows + -> Maybe Int -- ^ index of header separator + -> Parser (Table (DocH mod Identifier)) +tableStepThree width rs hdrIndex = do + cells <- loop (Set.singleton (0, 0)) + tableStepFour rs hdrIndex cells + where + height = length rs + + loop :: Set.Set (Int, Int) -> Parser [TC] + loop queue = case Set.minView queue of + Nothing -> return [] + Just ((y, x), queue') + | y + 1 >= height || x + 1 >= width -> loop queue' + | otherwise -> case scanRight x y of + Nothing -> loop queue' + Just (x2, y2) -> do + let tc = TC y x y2 x2 + fmap (tc :) $ loop $ queue' `Set.union` Set.fromList + [(y, x2), (y2, x), (y2, x2)] + + -- scan right looking for +, then try scan down + -- + -- do we need to record + saw on the way left and down? + scanRight :: Int -> Int -> Maybe (Int, Int) + scanRight x y = go (x + 1) where + bs = rs !! y + go x' | x' >= width = fail "overflow right " + | T.index bs x' == '+' = scanDown x y x' <|> go (x' + 1) + | T.index bs x' == '-' = go (x' + 1) + | otherwise = fail $ "not a border (right) " ++ show (x,y,x') + + -- scan down looking for + + scanDown :: Int -> Int -> Int -> Maybe (Int, Int) + scanDown x y x2 = go (y + 1) where + go y' | y' >= height = fail "overflow down" + | T.index (rs !! y') x2 == '+' = scanLeft x y x2 y' <|> go (y' + 1) + | T.index (rs !! y') x2 == '|' = go (y' + 1) + | otherwise = fail $ "not a border (down) " ++ show (x,y,x2,y') + + -- check that at y2 x..x2 characters are '+' or '-' + scanLeft :: Int -> Int -> Int -> Int -> Maybe (Int, Int) + scanLeft x y x2 y2 + | all (\x' -> T.index bs x' `elem` ['+', '-']) [x..x2] = scanUp x y x2 y2 + | otherwise = fail $ "not a border (left) " ++ show (x,y,x2,y2) + where + bs = rs !! y2 + + -- check that at y2 x..x2 characters are '+' or '-' + scanUp :: Int -> Int -> Int -> Int -> Maybe (Int, Int) + scanUp x y x2 y2 + | all (\y' -> T.index (rs !! y') x `elem` ['+', '|']) [y..y2] = return (x2, y2) + | otherwise = fail $ "not a border (up) " ++ show (x,y,x2,y2) + +-- | table cell: top left bottom right +data TC = TC !Int !Int !Int !Int + deriving Show + +tcXS :: TC -> [Int] +tcXS (TC _ x _ x2) = [x, x2] + +tcYS :: TC -> [Int] +tcYS (TC y _ y2 _) = [y, y2] + +-- | Fourth step. Given the locations of cells, forms 'Table' structure. +tableStepFour :: [Text] -> Maybe Int -> [TC] -> Parser (Table (DocH mod Identifier)) +tableStepFour rs hdrIndex cells = case hdrIndex of + Nothing -> return $ Table [] rowsDoc + Just i -> case elemIndex i yTabStops of + Nothing -> return $ Table [] rowsDoc + Just i' -> return $ uncurry Table $ splitAt i' rowsDoc + where + xTabStops = sortNub $ concatMap tcXS cells + yTabStops = sortNub $ concatMap tcYS cells + + sortNub :: Ord a => [a] -> [a] + sortNub = Set.toList . Set.fromList + + init' :: [a] -> [a] + init' [] = [] + init' [_] = [] + init' (x : xs) = x : init' xs + + rowsDoc = (fmap . fmap) parseParagraph rows + + rows = map makeRow (init' yTabStops) + where + makeRow y = TableRow $ mapMaybe (makeCell y) cells + makeCell y (TC y' x y2 x2) + | y /= y' = Nothing + | otherwise = Just $ TableCell xts yts (extract (x + 1) (y + 1) (x2 - 1) (y2 - 1)) + where + xts = length $ P.takeWhile (< x2) $ dropWhile (< x) xTabStops + yts = length $ P.takeWhile (< y2) $ dropWhile (< y) yTabStops + + -- extract cell contents given boundaries + extract :: Int -> Int -> Int -> Int -> Text + extract x y x2 y2 = T.intercalate "\n" + [ T.take (x2 - x + 1) $ T.drop x $ rs !! y' + | y' <- [y .. y2] + ] + +-- | Parse \@since annotations. since :: Parser (DocH mod a) since = ("@since " *> version <* skipHorizontalSpace <* endOfLine) >>= setSince >> return DocEmpty where - version = decimal `sepBy1'` "." + version = decimal `Parsec.sepBy1` "." -- | Headers inside the comment denoted with @=@ signs, up to 6 levels -- deep. @@ -280,38 +528,39 @@ since = ("@since " *> version <* skipHorizontalSpace <* endOfLine) >>= setSince -- Right (DocHeader (Header {headerLevel = 2, headerTitle = DocString "World"})) header :: Parser (DocH mod Identifier) header = do - let psers = map (string . encodeUtf8 . concat . flip replicate "=") [6, 5 .. 1] - pser = foldl1 (<|>) psers - delim <- decodeUtf8 <$> pser - line <- skipHorizontalSpace *> nonEmptyLine >>= return . parseString - rest <- paragraph <|> return DocEmpty + let psers = map (string . flip T.replicate "=") [6, 5 .. 1] + pser = choice' psers + delim <- T.unpack <$> pser + line <- skipHorizontalSpace *> nonEmptyLine >>= return . parseText + rest <- try paragraph <|> return DocEmpty return $ DocHeader (Header (length delim) line) `docAppend` rest textParagraph :: Parser (DocH mod Identifier) -textParagraph = parseString . intercalate "\n" <$> many1 nonEmptyLine +textParagraph = parseText . T.intercalate "\n" <$> some nonEmptyLine textParagraphThatStartsWithMarkdownLink :: Parser (DocH mod Identifier) textParagraphThatStartsWithMarkdownLink = docParagraph <$> (docAppend <$> markdownLink <*> optionalTextParagraph) where optionalTextParagraph :: Parser (DocH mod Identifier) - optionalTextParagraph = (docAppend <$> whitespace <*> textParagraph) <|> pure DocEmpty + optionalTextParagraph = choice' [ docAppend <$> whitespace <*> textParagraph + , pure DocEmpty ] whitespace :: Parser (DocH mod a) whitespace = DocString <$> (f <$> takeHorizontalSpace <*> optional "\n") where - f :: BS.ByteString -> Maybe BS.ByteString -> String + f :: Text -> Maybe Text -> String f xs (fromMaybe "" -> x) - | BS.null (xs <> x) = "" + | T.null (xs <> x) = "" | otherwise = " " -- | Parses unordered (bullet) lists. -unorderedList :: BS.ByteString -> Parser (DocH mod Identifier) +unorderedList :: Text -> Parser (DocH mod Identifier) unorderedList indent = DocUnorderedList <$> p where p = ("*" <|> "-") *> innerList indent p -- | Parses ordered lists (numbered or dashed). -orderedList :: BS.ByteString -> Parser (DocH mod Identifier) +orderedList :: Text -> Parser (DocH mod Identifier) orderedList indent = DocOrderedList <$> p where p = (paren <|> dot) *> innerList indent p @@ -323,104 +572,110 @@ orderedList indent = DocOrderedList <$> p -- same paragraph. Usually used as -- -- > someListFunction = listBeginning *> innerList someListFunction -innerList :: BS.ByteString -> Parser [DocH mod Identifier] +innerList :: Text -> Parser [DocH mod Identifier] -> Parser [DocH mod Identifier] innerList indent item = do c <- takeLine (cs, items) <- more indent item - let contents = docParagraph . parseString . dropNLs . unlines $ c : cs + let contents = docParagraph . parseText . dropNLs . T.unlines $ c : cs return $ case items of Left p -> [contents `docAppend` p] Right i -> contents : i -- | Parses definition lists. -definitionList :: BS.ByteString -> Parser (DocH mod Identifier) +definitionList :: Text -> Parser (DocH mod Identifier) definitionList indent = DocDefList <$> p where p = do - label <- "[" *> (parseStringBS <$> takeWhile1 (notInClass "]\n")) <* ("]" <* optional ":") + label <- "[" *> (parseParagraph <$> takeWhile1_ (`notElem` ("]\n" :: String))) <* ("]" <* optional ":") c <- takeLine (cs, items) <- more indent p - let contents = parseString . dropNLs . unlines $ c : cs + let contents = parseText . dropNLs . T.unlines $ c : cs return $ case items of Left x -> [(label, contents `docAppend` x)] Right i -> (label, contents) : i -- | Drops all trailing newlines. -dropNLs :: String -> String -dropNLs = reverse . dropWhile (== '\n') . reverse +dropNLs :: Text -> Text +dropNLs = T.dropWhileEnd (== '\n') -- | Main worker for 'innerList' and 'definitionList'. -- We need the 'Either' here to be able to tell in the respective functions -- whether we're dealing with the next list or a nested paragraph. -more :: Monoid a => BS.ByteString -> Parser a - -> Parser ([String], Either (DocH mod Identifier) a) -more indent item = innerParagraphs indent - <|> moreListItems indent item - <|> moreContent indent item - <|> pure ([], Right mempty) +more :: Monoid a => Text -> Parser a + -> Parser ([Text], Either (DocH mod Identifier) a) +more indent item = choice' [ innerParagraphs indent + , moreListItems indent item + , moreContent indent item + , pure ([], Right mempty) + ] -- | Used by 'innerList' and 'definitionList' to parse any nested paragraphs. -innerParagraphs :: BS.ByteString - -> Parser ([String], Either (DocH mod Identifier) a) +innerParagraphs :: Text + -> Parser ([Text], Either (DocH mod Identifier) a) innerParagraphs indent = (,) [] . Left <$> ("\n" *> indentedParagraphs indent) -- | Attempts to fetch the next list if possibly. Used by 'innerList' and -- 'definitionList' to recursively grab lists that aren't separated by a whole -- paragraph. -moreListItems :: BS.ByteString -> Parser a - -> Parser ([String], Either (DocH mod Identifier) a) +moreListItems :: Text -> Parser a + -> Parser ([Text], Either (DocH mod Identifier) a) moreListItems indent item = (,) [] . Right <$> indentedItem where - indentedItem = string indent *> skipSpace *> item + indentedItem = string indent *> Parsec.spaces *> item -- | Helper for 'innerList' and 'definitionList' which simply takes -- a line of text and attempts to parse more list content with 'more'. -moreContent :: Monoid a => BS.ByteString -> Parser a - -> Parser ([String], Either (DocH mod Identifier) a) +moreContent :: Monoid a => Text -> Parser a + -> Parser ([Text], Either (DocH mod Identifier) a) moreContent indent item = first . (:) <$> nonEmptyLine <*> more indent item -- | Parses an indented paragraph. -- The indentation is 4 spaces. -indentedParagraphs :: BS.ByteString -> Parser (DocH mod Identifier) +indentedParagraphs :: Text -> Parser (DocH mod Identifier) indentedParagraphs indent = - (concat <$> dropFrontOfPara indent') >>= parseParagraphs + (T.unpack . T.concat <$> dropFrontOfPara indent') >>= parseParagraphs where - indent' = string $ BS.append indent " " + indent' = string $ indent <> " " -- | Grab as many fully indented paragraphs as we can. -dropFrontOfPara :: Parser BS.ByteString -> Parser [String] +dropFrontOfPara :: Parser Text -> Parser [Text] dropFrontOfPara sp = do - currentParagraph <- some (sp *> takeNonEmptyLine) + currentParagraph <- some (try (sp *> takeNonEmptyLine)) followingParagraphs <- - skipHorizontalSpace *> nextPar -- we have more paragraphs to take - <|> skipHorizontalSpace *> nlList -- end of the ride, remember the newline - <|> endOfInput *> return [] -- nothing more to take at all + choice' [ skipHorizontalSpace *> nextPar -- we have more paragraphs to take + , skipHorizontalSpace *> nlList -- end of the ride, remember the newline + , Parsec.eof *> return [] -- nothing more to take at all + ] return (currentParagraph ++ followingParagraphs) where nextPar = (++) <$> nlList <*> dropFrontOfPara sp nlList = "\n" *> return ["\n"] -nonSpace :: BS.ByteString -> Parser BS.ByteString +nonSpace :: Text -> Parser Text nonSpace xs - | not $ any (not . isSpace) $ decodeUtf8 xs = fail "empty line" + | T.all isSpace xs = fail "empty line" | otherwise = return xs -- | Takes a non-empty, not fully whitespace line. -- -- Doesn't discard the trailing newline. -takeNonEmptyLine :: Parser String +takeNonEmptyLine :: Parser Text takeNonEmptyLine = do - (++ "\n") . decodeUtf8 <$> (takeWhile1 (/= '\n') >>= nonSpace) <* "\n" + l <- takeWhile1 (Parsec.noneOf "\n") >>= nonSpace + _ <- "\n" + pure (l <> "\n") -- | Takes indentation of first non-empty line. -- -- More precisely: skips all whitespace-only lines and returns indentation -- (horizontal space, might be empty) of that non-empty line. -takeIndent :: Parser BS.ByteString +takeIndent :: Parser Text takeIndent = do indent <- takeHorizontalSpace - "\n" *> takeIndent <|> return indent + choice' [ "\n" *> takeIndent + , return indent + ] -- | Blocks of text of the form: -- @@ -429,97 +684,98 @@ takeIndent = do -- >> baz -- birdtracks :: Parser (DocH mod a) -birdtracks = DocCodeBlock . DocString . intercalate "\n" . stripSpace <$> many1 line +birdtracks = DocCodeBlock . DocString . T.unpack . T.intercalate "\n" . stripSpace <$> some line where - line = skipHorizontalSpace *> ">" *> takeLine + line = try (skipHorizontalSpace *> ">" *> takeLine) -stripSpace :: [String] -> [String] +stripSpace :: [Text] -> [Text] stripSpace = fromMaybe <*> mapM strip' where - strip' (' ':xs') = Just xs' - strip' "" = Just "" - strip' _ = Nothing + strip' t = case T.uncons t of + Nothing -> Just "" + Just (' ',t') -> Just t' + _ -> Nothing -- | Parses examples. Examples are a paragraph level entitity (separated by an empty line). -- Consecutive examples are accepted. examples :: Parser (DocH mod a) -examples = DocExamples <$> (many (skipHorizontalSpace *> "\n") *> go) +examples = DocExamples <$> (many (try (skipHorizontalSpace *> "\n")) *> go) where go :: Parser [Example] go = do - prefix <- decodeUtf8 <$> takeHorizontalSpace <* ">>>" + prefix <- takeHorizontalSpace <* ">>>" expr <- takeLine (rs, es) <- resultAndMoreExamples return (makeExample prefix expr rs : es) where - resultAndMoreExamples :: Parser ([String], [Example]) - resultAndMoreExamples = moreExamples <|> result <|> pure ([], []) + resultAndMoreExamples :: Parser ([Text], [Example]) + resultAndMoreExamples = choice' [ moreExamples, result, pure ([], []) ] where - moreExamples :: Parser ([String], [Example]) + moreExamples :: Parser ([Text], [Example]) moreExamples = (,) [] <$> go - result :: Parser ([String], [Example]) + result :: Parser ([Text], [Example]) result = first . (:) <$> nonEmptyLine <*> resultAndMoreExamples - makeExample :: String -> String -> [String] -> Example + makeExample :: Text -> Text -> [Text] -> Example makeExample prefix expression res = - Example (strip expression) result + Example (T.unpack (T.strip expression)) result where - result = map (substituteBlankLine . tryStripPrefix) res + result = map (T.unpack . substituteBlankLine . tryStripPrefix) res - tryStripPrefix xs = fromMaybe xs (stripPrefix prefix xs) + tryStripPrefix xs = fromMaybe xs (T.stripPrefix prefix xs) substituteBlankLine "<BLANKLINE>" = "" substituteBlankLine xs = xs -nonEmptyLine :: Parser String -nonEmptyLine = mfilter (any (not . isSpace)) takeLine +nonEmptyLine :: Parser Text +nonEmptyLine = try (mfilter (T.any (not . isSpace)) takeLine) -takeLine :: Parser String -takeLine = decodeUtf8 <$> takeWhile (/= '\n') <* endOfLine +takeLine :: Parser Text +takeLine = try (takeWhile (Parsec.noneOf "\n") <* endOfLine) endOfLine :: Parser () -endOfLine = void "\n" <|> endOfInput +endOfLine = void "\n" <|> Parsec.eof -- | Property parser. -- -- >>> snd <$> parseOnly property "prop> hello world" -- Right (DocProperty "hello world") property :: Parser (DocH mod a) -property = DocProperty . strip . decodeUtf8 <$> ("prop>" *> takeWhile1 (/= '\n')) +property = DocProperty . T.unpack . T.strip <$> ("prop>" *> takeWhile1 (Parsec.noneOf "\n")) -- | -- Paragraph level codeblock. Anything between the two delimiting \@ is parsed -- for markup. codeblock :: Parser (DocH mod Identifier) codeblock = - DocCodeBlock . parseStringBS . dropSpaces + DocCodeBlock . parseParagraph . dropSpaces <$> ("@" *> skipHorizontalSpace *> "\n" *> block' <* "@") where dropSpaces xs = - let rs = decodeUtf8 xs - in case splitByNl rs of + case splitByNl xs of [] -> xs - ys -> case last ys of - ' ':_ -> case mapM dropSpace ys of - Nothing -> xs - Just zs -> encodeUtf8 $ intercalate "\n" zs + ys -> case T.uncons (last ys) of + Just (' ',_) -> case mapM dropSpace ys of + Nothing -> xs + Just zs -> T.intercalate "\n" zs _ -> xs -- This is necessary because ‘lines’ swallows up a trailing newline -- and we lose information about whether the last line belongs to @ or to -- text which we need to decide whether we actually want to be dropping -- anything at all. - splitByNl = unfoldr (\x -> case x of - '\n':s -> Just (span (/= '\n') s) - _ -> Nothing) - . ('\n' :) + splitByNl = unfoldr (\x -> case T.uncons x of + Just ('\n',x') -> Just (T.span (/= '\n') x') + _ -> Nothing) + . ("\n" <>) - dropSpace "" = Just "" - dropSpace (' ':xs) = Just xs - dropSpace _ = Nothing + dropSpace t = case T.uncons t of + Nothing -> Just "" + Just (' ',t') -> Just t' + _ -> Nothing - block' = scan False p + block' = scan p False where p isNewline c | isNewline && c == '@' = Nothing @@ -527,10 +783,12 @@ codeblock = | otherwise = Just $ c == '\n' hyperlink :: Parser (DocH mod a) -hyperlink = DocHyperlink . makeLabeled Hyperlink . decodeUtf8 - <$> disallowNewline ("<" *> takeUntil ">") - <|> autoUrl - <|> markdownLink +hyperlink = choice' [ angleBracketLink, markdownLink, autoUrl ] + +angleBracketLink :: Parser (DocH mod a) +angleBracketLink = + DocHyperlink . makeLabeled Hyperlink + <$> disallowNewline ("<" *> takeUntil ">") markdownLink :: Parser (DocH mod a) markdownLink = DocHyperlink <$> linkParser @@ -539,7 +797,7 @@ linkParser :: Parser Hyperlink linkParser = flip Hyperlink <$> label <*> (whitespace *> url) where label :: Parser (Maybe String) - label = Just . strip . decode <$> ("[" *> takeUntil "]") + label = Just . decode . T.strip <$> ("[" *> takeUntil "]") whitespace :: Parser () whitespace = skipHorizontalSpace <* optional ("\n" *> skipHorizontalSpace) @@ -550,19 +808,25 @@ linkParser = flip Hyperlink <$> label <*> (whitespace *> url) rejectWhitespace :: MonadPlus m => m String -> m String rejectWhitespace = mfilter (all (not . isSpace)) - decode :: BS.ByteString -> String - decode = removeEscapes . decodeUtf8 + decode :: Text -> String + decode = T.unpack . removeEscapes -- | Looks for URL-like things to automatically hyperlink even if they -- weren't marked as links. autoUrl :: Parser (DocH mod a) autoUrl = mkLink <$> url where - url = mappend <$> ("http://" <|> "https://" <|> "ftp://") <*> takeWhile1 (not . isSpace) - mkLink :: BS.ByteString -> DocH mod a - mkLink s = case unsnoc s of - Just (xs, x) | inClass ",.!?" x -> DocHyperlink (Hyperlink (decodeUtf8 xs) Nothing) `docAppend` DocString [x] - _ -> DocHyperlink (Hyperlink (decodeUtf8 s) Nothing) + url = mappend <$> choice' [ "http://", "https://", "ftp://"] <*> takeWhile1 (Parsec.satisfy (not . isSpace)) + + mkLink :: Text -> DocH mod a + mkLink s = case T.unsnoc s of + Just (xs,x) | x `elem` (",.!?" :: String) -> DocHyperlink (mkHyperlink xs) `docAppend` DocString [x] + _ -> DocHyperlink (mkHyperlink s) + + mkHyperlink :: Text -> Hyperlink + mkHyperlink lnk = Hyperlink (T.unpack lnk) Nothing + + -- | Parses strings between identifier delimiters. Consumes all input that it -- deems to be valid in an identifier. Note that it simply blindly consumes @@ -570,26 +834,16 @@ autoUrl = mkLink <$> url parseValid :: Parser String parseValid = p some where - idChar = - satisfy (\c -> isAlpha_ascii c - || isDigit c - -- N.B. '-' is placed first otherwise attoparsec thinks - -- it belongs to a character class - || inClass "-_.!#$%&*+/<=>?@\\|~:^" c) + idChar = Parsec.satisfy (\c -> isAlphaNum c || isSymbolChar c || c == '_') p p' = do - vs' <- p' $ utf8String "⋆" <|> return <$> idChar - let vs = concat vs' + vs <- p' idChar c <- peekChar' case c of '`' -> return vs - '\'' -> (\x -> vs ++ "'" ++ x) <$> ("'" *> p many') <|> return vs + '\'' -> choice' [ (\x -> vs ++ "'" ++ x) <$> ("'" *> p many), return vs ] _ -> fail "outofvalid" --- | Parses UTF8 strings from ByteString streams. -utf8String :: String -> Parser String -utf8String x = decodeUtf8 <$> string (encodeUtf8 x) - -- | Parses identifiers with help of 'parseValid'. Asks GHC for -- 'String' from the string it deems valid. identifier :: Parser (DocH mod Identifier) @@ -599,4 +853,4 @@ identifier = do e <- idDelim return $ DocIdentifier (o, vid, e) where - idDelim = satisfy (\c -> c == '\'' || c == '`') + idDelim = Parsec.satisfy (\c -> c == '\'' || c == '`') diff --git a/haddock-library/src/Documentation/Haddock/Parser/Monad.hs b/haddock-library/src/Documentation/Haddock/Parser/Monad.hs index 3f7d60f8..585c76bb 100644 --- a/haddock-library/src/Documentation/Haddock/Parser/Monad.hs +++ b/haddock-library/src/Documentation/Haddock/Parser/Monad.hs @@ -1,149 +1,91 @@ -{-# LANGUAGE GeneralizedNewtypeDeriving, TypeFamilies #-} -module Documentation.Haddock.Parser.Monad ( - module Documentation.Haddock.Parser.Monad -, Attoparsec.isDigit -, Attoparsec.isDigit_w8 -, Attoparsec.isAlpha_iso8859_15 -, Attoparsec.isAlpha_ascii -, Attoparsec.isSpace -, Attoparsec.isSpace_w8 -, Attoparsec.inClass -, Attoparsec.notInClass -, Attoparsec.isEndOfLine -, Attoparsec.isHorizontalSpace -, Attoparsec.choice -, Attoparsec.count -, Attoparsec.option -, Attoparsec.many' -, Attoparsec.many1 -, Attoparsec.many1' -, Attoparsec.manyTill -, Attoparsec.manyTill' -, Attoparsec.sepBy -, Attoparsec.sepBy' -, Attoparsec.sepBy1 -, Attoparsec.sepBy1' -, Attoparsec.skipMany -, Attoparsec.skipMany1 -, Attoparsec.eitherP -) where - -import Control.Applicative -import Control.Monad -import Data.String -import Data.ByteString (ByteString) -import qualified Data.ByteString.Lazy as LB -import qualified Data.Attoparsec.ByteString.Char8 as Attoparsec -import Control.Monad.Trans.State -import qualified Control.Monad.Trans.Class as Trans -import Data.Word -import Data.Bits -import Data.Tuple - -import Documentation.Haddock.Types (Version) +{-# LANGUAGE GeneralizedNewtypeDeriving #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE BangPatterns #-} +{-# LANGUAGE TypeSynonymInstances #-} -newtype ParserState = ParserState { - parserStateSince :: Maybe Version -} deriving (Eq, Show) +module Documentation.Haddock.Parser.Monad where -initialParserState :: ParserState -initialParserState = ParserState Nothing +import qualified Text.Parsec.Char as Parsec +import qualified Text.Parsec as Parsec -newtype Parser a = Parser (StateT ParserState Attoparsec.Parser a) - deriving (Functor, Applicative, Alternative, Monad, MonadPlus) +import qualified Data.Text as T +import Data.Text ( Text ) -instance (a ~ ByteString) => IsString (Parser a) where - fromString = lift . fromString +import Data.String ( IsString(..) ) +import Data.Bits ( Bits(..) ) +import Data.Char ( ord ) +import Data.List ( foldl' ) -parseOnly :: Parser a -> ByteString -> Either String (ParserState, a) -parseOnly (Parser p) = fmap swap . Attoparsec.parseOnly (runStateT p initialParserState) +import Documentation.Haddock.Types ( Version ) -lift :: Attoparsec.Parser a -> Parser a -lift = Parser . Trans.lift +newtype ParserState = ParserState { + parserStateSince :: Maybe Version +} deriving (Eq, Show) -setParserState :: ParserState -> Parser () -setParserState = Parser . put +initialParserState :: ParserState +initialParserState = ParserState Nothing setSince :: Version -> Parser () -setSince since = Parser $ modify (\st -> st {parserStateSince = Just since}) - -char :: Char -> Parser Char -char = lift . Attoparsec.char - -char8 :: Char -> Parser Word8 -char8 = lift . Attoparsec.char8 +setSince since = Parsec.modifyState (\st -> st {parserStateSince = Just since}) -anyChar :: Parser Char -anyChar = lift Attoparsec.anyChar +type Parser = Parsec.Parsec Text ParserState -notChar :: Char -> Parser Char -notChar = lift . Attoparsec.notChar +instance (a ~ Text) => IsString (Parser a) where + fromString = fmap T.pack . Parsec.string -satisfy :: (Char -> Bool) -> Parser Char -satisfy = lift . Attoparsec.satisfy +parseOnly :: Parser a -> Text -> Either String (ParserState, a) +parseOnly p t = case Parsec.runParser p' initialParserState "<haddock>" t of + Left e -> Left (show e) + Right (x,s) -> Right (s,x) + where p' = (,) <$> p <*> Parsec.getState +-- | Always succeeds, but returns 'Nothing' if at the end of input. Does not +-- consume input. peekChar :: Parser (Maybe Char) -peekChar = lift Attoparsec.peekChar +peekChar = Parsec.optionMaybe . Parsec.try . Parsec.lookAhead $ Parsec.anyChar +-- | Fails if at the end of input. Does not consume input. peekChar' :: Parser Char -peekChar' = lift Attoparsec.peekChar' - -digit :: Parser Char -digit = lift Attoparsec.digit - -letter_iso8859_15 :: Parser Char -letter_iso8859_15 = lift Attoparsec.letter_iso8859_15 - -letter_ascii :: Parser Char -letter_ascii = lift Attoparsec.letter_ascii - -space :: Parser Char -space = lift Attoparsec.space - -string :: ByteString -> Parser ByteString -string = lift . Attoparsec.string - -stringCI :: ByteString -> Parser ByteString -stringCI = lift . Attoparsec.stringCI - -skipSpace :: Parser () -skipSpace = lift Attoparsec.skipSpace - -skipWhile :: (Char -> Bool) -> Parser () -skipWhile = lift . Attoparsec.skipWhile - -take :: Int -> Parser ByteString -take = lift . Attoparsec.take - -scan :: s -> (s -> Char -> Maybe s) -> Parser ByteString -scan s = lift . Attoparsec.scan s - -takeWhile :: (Char -> Bool) -> Parser ByteString -takeWhile = lift . Attoparsec.takeWhile - -takeWhile1 :: (Char -> Bool) -> Parser ByteString -takeWhile1 = lift . Attoparsec.takeWhile1 - -takeTill :: (Char -> Bool) -> Parser ByteString -takeTill = lift . Attoparsec.takeTill - -takeByteString :: Parser ByteString -takeByteString = lift Attoparsec.takeByteString - -takeLazyByteString :: Parser LB.ByteString -takeLazyByteString = lift Attoparsec.takeLazyByteString - -endOfLine :: Parser () -endOfLine = lift Attoparsec.endOfLine - +peekChar' = Parsec.lookAhead Parsec.anyChar + +-- | Parses the given string. Returns the parsed string. +string :: Text -> Parser Text +string t = Parsec.string (T.unpack t) *> pure t + +-- | Scan the input text, accumulating characters as long as the scanning +-- function returns true. +scan :: (s -> Char -> Maybe s) -- ^ scan function + -> s -- ^ initial state + -> Parser Text +scan f = fmap T.pack . go + where go s1 = do { cOpt <- peekChar + ; case cOpt >>= f s1 of + Nothing -> pure "" + Just s2 -> (:) <$> Parsec.anyChar <*> go s2 + } + +-- | Apply a parser for a character zero or more times and collect the result in +-- a string. +takeWhile :: Parser Char -> Parser Text +takeWhile = fmap T.pack . Parsec.many + +-- | Apply a parser for a character one or more times and collect the result in +-- a string. +takeWhile1 :: Parser Char -> Parser Text +takeWhile1 = fmap T.pack . Parsec.many1 + +-- | Parse a decimal number. decimal :: Integral a => Parser a -decimal = lift Attoparsec.decimal +decimal = foldl' step 0 `fmap` Parsec.many1 Parsec.digit + where step a c = a * 10 + fromIntegral (ord c - 48) +-- | Parse a hexadecimal number. hexadecimal :: (Integral a, Bits a) => Parser a -hexadecimal = lift Attoparsec.hexadecimal - -endOfInput :: Parser () -endOfInput = lift Attoparsec.endOfInput - -atEnd :: Parser Bool -atEnd = lift Attoparsec.atEnd +hexadecimal = foldl' step 0 `fmap` Parsec.many1 Parsec.hexDigit + where + step a c | w >= 48 && w <= 57 = (a `shiftL` 4) .|. fromIntegral (w - 48) + | w >= 97 = (a `shiftL` 4) .|. fromIntegral (w - 87) + | otherwise = (a `shiftL` 4) .|. fromIntegral (w - 55) + where w = ord c diff --git a/haddock-library/src/Documentation/Haddock/Parser/Util.hs b/haddock-library/src/Documentation/Haddock/Parser/Util.hs index ab5e5e9e..ffa91b09 100644 --- a/haddock-library/src/Documentation/Haddock/Parser/Util.hs +++ b/haddock-library/src/Documentation/Haddock/Parser/Util.hs @@ -1,4 +1,4 @@ -{-# LANGUAGE CPP #-} +{-# LANGUAGE OverloadedStrings #-} -- | -- Module : Documentation.Haddock.Parser.Util -- Copyright : (c) Mateusz Kowalczyk 2013-2014, @@ -11,62 +11,59 @@ -- -- Various utility functions used by the parser. module Documentation.Haddock.Parser.Util ( - unsnoc -, strip -, takeUntil -, removeEscapes -, makeLabeled -, takeHorizontalSpace -, skipHorizontalSpace + takeUntil, + removeEscapes, + makeLabeled, + takeHorizontalSpace, + skipHorizontalSpace, ) where +import qualified Text.Parsec as Parsec + +import qualified Data.Text as T +import Data.Text (Text) + import Control.Applicative import Control.Monad (mfilter) -import Documentation.Haddock.Parser.Monad hiding (isHorizontalSpace) -import Data.ByteString.Char8 (ByteString) -import qualified Data.ByteString.Char8 as BS +import Documentation.Haddock.Parser.Monad import Prelude hiding (takeWhile) -#if MIN_VERSION_bytestring(0,10,2) -import Data.ByteString.Char8 (unsnoc) -#else -unsnoc :: ByteString -> Maybe (ByteString, Char) -unsnoc bs - | BS.null bs = Nothing - | otherwise = Just (BS.init bs, BS.last bs) -#endif +import Data.Char (isSpace) --- | Remove all leading and trailing whitespace -strip :: String -> String -strip = (\f -> f . f) $ dropWhile isSpace . reverse - -isHorizontalSpace :: Char -> Bool -isHorizontalSpace = inClass " \t\f\v\r" +-- | Characters that count as horizontal space +horizontalSpace :: [Char] +horizontalSpace = " \t\f\v\r" +-- | Skip and ignore leading horizontal space skipHorizontalSpace :: Parser () -skipHorizontalSpace = skipWhile isHorizontalSpace +skipHorizontalSpace = Parsec.skipMany (Parsec.oneOf horizontalSpace) -takeHorizontalSpace :: Parser BS.ByteString -takeHorizontalSpace = takeWhile isHorizontalSpace +-- | Take leading horizontal space +takeHorizontalSpace :: Parser Text +takeHorizontalSpace = takeWhile (Parsec.oneOf horizontalSpace) -makeLabeled :: (String -> Maybe String -> a) -> String -> a -makeLabeled f input = case break isSpace $ removeEscapes $ strip input of - (uri, "") -> f uri Nothing - (uri, label) -> f uri (Just $ dropWhile isSpace label) +makeLabeled :: (String -> Maybe String -> a) -> Text -> a +makeLabeled f input = case T.break isSpace $ removeEscapes $ T.strip input of + (uri, "") -> f (T.unpack uri) Nothing + (uri, label) -> f (T.unpack uri) (Just . T.unpack $ T.stripStart label) -- | Remove escapes from given string. -- -- Only do this if you do not process (read: parse) the input any further. -removeEscapes :: String -> String -removeEscapes "" = "" -removeEscapes ('\\':'\\':xs) = '\\' : removeEscapes xs -removeEscapes ('\\':xs) = removeEscapes xs -removeEscapes (x:xs) = x : removeEscapes xs +removeEscapes :: Text -> Text +removeEscapes = T.unfoldr go + where + go :: Text -> Maybe (Char, Text) + go xs = case T.uncons xs of + Just ('\\',ys) -> T.uncons ys + unconsed -> unconsed -takeUntil :: ByteString -> Parser ByteString -takeUntil end_ = dropEnd <$> requireEnd (scan (False, end) p) >>= gotSome +-- | Consume characters from the input up to and including the given pattern. +-- Return everything consumed except for the end pattern itself. +takeUntil :: Text -> Parser Text +takeUntil end_ = T.dropEnd (T.length end_) <$> requireEnd (scan p (False, end)) >>= gotSome where - end = BS.unpack end_ + end = T.unpack end_ p :: (Bool, String) -> Char -> Maybe (Bool, String) p acc c = case acc of @@ -75,9 +72,8 @@ takeUntil end_ = dropEnd <$> requireEnd (scan (False, end) p) >>= gotSome (_, x:xs) | x == c -> Just (False, xs) _ -> Just (c == '\\', end) - dropEnd = BS.reverse . BS.drop (length end) . BS.reverse - requireEnd = mfilter (BS.isSuffixOf end_) + requireEnd = mfilter (T.isSuffixOf end_) gotSome xs - | BS.null xs = fail "didn't get any content" + | T.null xs = fail "didn't get any content" | otherwise = return xs diff --git a/haddock-library/src/Documentation/Haddock/Types.hs b/haddock-library/src/Documentation/Haddock/Types.hs index 1e76c631..b5dea3d4 100644 --- a/haddock-library/src/Documentation/Haddock/Types.hs +++ b/haddock-library/src/Documentation/Haddock/Types.hs @@ -15,6 +15,7 @@ module Documentation.Haddock.Types where #if !MIN_VERSION_base(4,8,0) +import Control.Applicative import Data.Foldable import Data.Traversable #endif @@ -33,7 +34,9 @@ import Data.Bitraversable -- meta-data to comments. We make a structure for this ahead of time -- so we don't have to gut half the core each time we want to add such -- info. -newtype Meta = Meta { _version :: Maybe Version } deriving (Eq, Show) +data Meta = Meta { _version :: Maybe Version + , _package :: Maybe Package + } deriving (Eq, Show) data MetaDoc mod id = MetaDoc { _meta :: Meta @@ -60,6 +63,7 @@ overDocF :: Functor f => (DocH a b -> f (DocH c d)) -> MetaDoc a b -> f (MetaDoc overDocF f d = (\x -> d { _doc = x }) <$> f (_doc d) type Version = [Int] +type Package = String data Hyperlink = Hyperlink { hyperlinkUrl :: String @@ -81,6 +85,21 @@ data Example = Example , exampleResult :: [String] } deriving (Eq, Show) +data TableCell id = TableCell + { tableCellColspan :: Int + , tableCellRowspan :: Int + , tableCellContents :: id + } deriving (Eq, Show, Functor, Foldable, Traversable) + +newtype TableRow id = TableRow + { tableRowCells :: [TableCell id] + } deriving (Eq, Show, Functor, Foldable, Traversable) + +data Table id = Table + { tableHeaderRows :: [TableRow id] + , tableBodyRows :: [TableRow id] + } deriving (Eq, Show, Functor, Foldable, Traversable) + data DocH mod id = DocEmpty | DocAppend (DocH mod id) (DocH mod id) @@ -88,8 +107,10 @@ data DocH mod id | DocParagraph (DocH mod id) | DocIdentifier id | DocIdentifierUnchecked mod + -- ^ A qualified identifier that couldn't be resolved. | DocModule String | DocWarning (DocH mod id) + -- ^ This constructor has no counterpart in Haddock markup. | DocEmphasis (DocH mod id) | DocMonospaced (DocH mod id) | DocBold (DocH mod id) @@ -102,9 +123,11 @@ data DocH mod id | DocMathInline String | DocMathDisplay String | DocAName String + -- ^ A (HTML) anchor. | DocProperty String | DocExamples [Example] | DocHeader (Header (DocH mod id)) + | DocTable (Table (DocH mod id)) deriving (Eq, Show, Functor, Foldable, Traversable) #if MIN_VERSION_base(4,8,0) @@ -132,6 +155,7 @@ instance Bifunctor DocH where bimap _ _ (DocProperty s) = DocProperty s bimap _ _ (DocExamples examples) = DocExamples examples bimap f g (DocHeader (Header level title)) = DocHeader (Header level (bimap f g title)) + bimap f g (DocTable (Table header body)) = DocTable (Table (map (fmap (bimap f g)) header) (map (fmap (bimap f g)) body)) #endif #if MIN_VERSION_base(4,10,0) @@ -149,6 +173,7 @@ instance Bifoldable DocH where bifoldr f g z (DocDefList docs) = foldr (\(l, r) acc -> bifoldr f g (bifoldr f g acc l) r) z docs bifoldr f g z (DocCodeBlock doc) = bifoldr f g z doc bifoldr f g z (DocHeader (Header _ title)) = bifoldr f g z title + bifoldr f g z (DocTable (Table header body)) = foldr (\r acc -> foldr (flip (bifoldr f g)) acc r) (foldr (\r acc -> foldr (flip (bifoldr f g)) acc r) z body) header bifoldr _ _ z _ = z instance Bitraversable DocH where @@ -175,6 +200,7 @@ instance Bitraversable DocH where bitraverse _ _ (DocProperty s) = pure (DocProperty s) bitraverse _ _ (DocExamples examples) = pure (DocExamples examples) bitraverse f g (DocHeader (Header level title)) = (DocHeader . Header level) <$> bitraverse f g title + bitraverse f g (DocTable (Table header body)) = (\h b -> DocTable (Table h b)) <$> traverse (traverse (bitraverse f g)) header <*> traverse (traverse (bitraverse f g)) body #endif -- | 'DocMarkupH' is a set of instructions for marking up documentation. @@ -209,4 +235,5 @@ data DocMarkupH mod id a = Markup , markupProperty :: String -> a , markupExample :: [Example] -> a , markupHeader :: Header a -> a + , markupTable :: Table a -> a } diff --git a/haddock-library/test/Documentation/Haddock/ParserSpec.hs b/haddock-library/test/Documentation/Haddock/ParserSpec.hs index b63ece92..86ed3b35 100644 --- a/haddock-library/test/Documentation/Haddock/ParserSpec.hs +++ b/haddock-library/test/Documentation/Haddock/ParserSpec.hs @@ -10,6 +10,8 @@ import Documentation.Haddock.Doc (docAppend) import Test.Hspec import Test.QuickCheck +import Prelude hiding ((<>)) + infixr 6 <> (<>) :: Doc id -> Doc id -> Doc id (<>) = docAppend @@ -22,8 +24,15 @@ instance IsString (Doc String) where instance IsString a => IsString (Maybe a) where fromString = Just . fromString +emptyMeta :: Meta +emptyMeta = + Meta { + _version = Nothing + , _package = Nothing + } + parseParas :: String -> MetaDoc () String -parseParas = overDoc Parse.toRegular . Parse.parseParas +parseParas = overDoc Parse.toRegular . Parse.parseParas Nothing parseString :: String -> Doc String parseString = Parse.toRegular . Parse.parseString @@ -373,17 +382,17 @@ spec = do context "when parsing @since" $ do it "adds specified version to the result" $ do parseParas "@since 0.5.0" `shouldBe` - MetaDoc { _meta = Meta { _version = Just [0,5,0] } + MetaDoc { _meta = emptyMeta { _version = Just [0,5,0] } , _doc = DocEmpty } it "ignores trailing whitespace" $ do parseParas "@since 0.5.0 \t " `shouldBe` - MetaDoc { _meta = Meta { _version = Just [0,5,0] } + MetaDoc { _meta = emptyMeta { _version = Just [0,5,0] } , _doc = DocEmpty } it "does not allow trailing input" $ do parseParas "@since 0.5.0 foo" `shouldBe` - MetaDoc { _meta = Meta { _version = Nothing } + MetaDoc { _meta = emptyMeta { _version = Nothing } , _doc = DocParagraph "@since 0.5.0 foo" } @@ -393,7 +402,7 @@ spec = do "@since 0.5.0" , "@since 0.6.0" , "@since 0.7.0" - ] `shouldBe` MetaDoc { _meta = Meta { _version = Just [0,7,0] } + ] `shouldBe` MetaDoc { _meta = emptyMeta { _version = Just [0,7,0] } , _doc = DocEmpty } diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec.hs b/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec.hs deleted file mode 100644 index bd3c5592..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec.hs +++ /dev/null @@ -1,23 +0,0 @@ --- | --- Module : Data.Attoparsec --- Copyright : Bryan O'Sullivan 2007-2015 --- License : BSD3 --- --- Maintainer : bos@serpentine.com --- Stability : experimental --- Portability : unknown --- --- Simple, efficient combinator parsing for --- 'Data.ByteString.ByteString' strings, loosely based on the Parsec --- library. --- --- This module is deprecated. Use "Data.Attoparsec.ByteString" --- instead. - -module Data.Attoparsec - {-# DEPRECATED "This module will be removed in the next major release." #-} - ( - module Data.Attoparsec.ByteString - ) where - -import Data.Attoparsec.ByteString diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString.hs b/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString.hs deleted file mode 100644 index 84e567d9..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString.hs +++ /dev/null @@ -1,230 +0,0 @@ -{-# LANGUAGE CPP #-} -#if __GLASGOW_HASKELL__ >= 702 -{-# LANGUAGE Trustworthy #-} -#endif --- | --- Module : Data.Attoparsec.ByteString --- Copyright : Bryan O'Sullivan 2007-2015 --- License : BSD3 --- --- Maintainer : bos@serpentine.com --- Stability : experimental --- Portability : unknown --- --- Simple, efficient combinator parsing for 'B.ByteString' strings, --- loosely based on the Parsec library. - -module Data.Attoparsec.ByteString - ( - -- * Differences from Parsec - -- $parsec - - -- * Incremental input - -- $incremental - - -- * Performance considerations - -- $performance - - -- * Parser types - I.Parser - , Result - , T.IResult(..) - , I.compareResults - - -- * Running parsers - , parse - , feed - , I.parseOnly - , parseWith - , parseTest - - -- ** Result conversion - , maybeResult - , eitherResult - - -- * Parsing individual bytes - , I.word8 - , I.anyWord8 - , I.notWord8 - , I.satisfy - , I.satisfyWith - , I.skip - - -- ** Lookahead - , I.peekWord8 - , I.peekWord8' - - -- ** Byte classes - , I.inClass - , I.notInClass - - -- * Efficient string handling - , I.string - , I.skipWhile - , I.take - , I.scan - , I.runScanner - , I.takeWhile - , I.takeWhile1 - , I.takeTill - - -- ** Consume all remaining input - , I.takeByteString - , I.takeLazyByteString - - -- * Combinators - , try - , (<?>) - , choice - , count - , option - , many' - , many1 - , many1' - , manyTill - , manyTill' - , sepBy - , sepBy' - , sepBy1 - , sepBy1' - , skipMany - , skipMany1 - , eitherP - , I.match - -- * State observation and manipulation functions - , I.endOfInput - , I.atEnd - ) where - -import Data.Attoparsec.Combinator -import Data.List (intercalate) -import qualified Data.Attoparsec.ByteString.Internal as I -import qualified Data.Attoparsec.Internal as I -import qualified Data.ByteString as B -import Data.Attoparsec.ByteString.Internal (Result, parse) -import qualified Data.Attoparsec.Internal.Types as T - --- $parsec --- --- Compared to Parsec 3, attoparsec makes several tradeoffs. It is --- not intended for, or ideal for, all possible uses. --- --- * While attoparsec can consume input incrementally, Parsec cannot. --- Incremental input is a huge deal for efficient and secure network --- and system programming, since it gives much more control to users --- of the library over matters such as resource usage and the I/O --- model to use. --- --- * Much of the performance advantage of attoparsec is gained via --- high-performance parsers such as 'I.takeWhile' and 'I.string'. --- If you use complicated combinators that return lists of bytes or --- characters, there is less performance difference between the two --- libraries. --- --- * Unlike Parsec 3, attoparsec does not support being used as a --- monad transformer. --- --- * attoparsec is specialised to deal only with strict 'B.ByteString' --- input. Efficiency concerns rule out both lists and lazy --- bytestrings. The usual use for lazy bytestrings would be to --- allow consumption of very large input without a large footprint. --- For this need, attoparsec's incremental input provides an --- excellent substitute, with much more control over when input --- takes place. If you must use lazy bytestrings, see the --- "Data.Attoparsec.ByteString.Lazy" module, which feeds lazy chunks --- to a regular parser. --- --- * Parsec parsers can produce more helpful error messages than --- attoparsec parsers. This is a matter of focus: attoparsec avoids --- the extra book-keeping in favour of higher performance. - --- $incremental --- --- attoparsec supports incremental input, meaning that you can feed it --- a bytestring that represents only part of the expected total amount --- of data to parse. If your parser reaches the end of a fragment of --- input and could consume more input, it will suspend parsing and --- return a 'T.Partial' continuation. --- --- Supplying the 'T.Partial' continuation with a bytestring will --- resume parsing at the point where it was suspended, with the --- bytestring you supplied used as new input at the end of the --- existing input. You must be prepared for the result of the resumed --- parse to be another 'T.Partial' continuation. --- --- To indicate that you have no more input, supply the 'T.Partial' --- continuation with an empty bytestring. --- --- Remember that some parsing combinators will not return a result --- until they reach the end of input. They may thus cause 'T.Partial' --- results to be returned. --- --- If you do not need support for incremental input, consider using --- the 'I.parseOnly' function to run your parser. It will never --- prompt for more input. --- --- /Note/: incremental input does /not/ imply that attoparsec will --- release portions of its internal state for garbage collection as it --- proceeds. Its internal representation is equivalent to a single --- 'ByteString': if you feed incremental input to a parser, it will --- require memory proportional to the amount of input you supply. --- (This is necessary to support arbitrary backtracking.) - --- $performance --- --- If you write an attoparsec-based parser carefully, it can be --- realistic to expect it to perform similarly to a hand-rolled C --- parser (measuring megabytes parsed per second). --- --- To actually achieve high performance, there are a few guidelines --- that it is useful to follow. --- --- Use the 'B.ByteString'-oriented parsers whenever possible, --- e.g. 'I.takeWhile1' instead of 'many1' 'I.anyWord8'. There is --- about a factor of 100 difference in performance between the two --- kinds of parser. --- --- For very simple byte-testing predicates, write them by hand instead --- of using 'I.inClass' or 'I.notInClass'. For instance, both of --- these predicates test for an end-of-line byte, but the first is --- much faster than the second: --- --- >endOfLine_fast w = w == 13 || w == 10 --- >endOfLine_slow = inClass "\r\n" --- --- Make active use of benchmarking and profiling tools to measure, --- find the problems with, and improve the performance of your parser. - --- | Run a parser and print its result to standard output. -parseTest :: (Show a) => I.Parser a -> B.ByteString -> IO () -parseTest p s = print (parse p s) - --- | Run a parser with an initial input string, and a monadic action --- that can supply more input if needed. -parseWith :: Monad m => - (m B.ByteString) - -- ^ An action that will be executed to provide the parser - -- with more input, if necessary. The action must return an - -- 'B.empty' string when there is no more input available. - -> I.Parser a - -> B.ByteString - -- ^ Initial input for the parser. - -> m (Result a) -parseWith refill p s = step $ parse p s - where step (T.Partial k) = (step . k) =<< refill - step r = return r -{-# INLINE parseWith #-} - --- | Convert a 'Result' value to a 'Maybe' value. A 'T.Partial' result --- is treated as failure. -maybeResult :: Result r -> Maybe r -maybeResult (T.Done _ r) = Just r -maybeResult _ = Nothing - --- | Convert a 'Result' value to an 'Either' value. A 'T.Partial' --- result is treated as failure. -eitherResult :: Result r -> Either String r -eitherResult (T.Done _ r) = Right r -eitherResult (T.Fail _ [] msg) = Left msg -eitherResult (T.Fail _ ctxs msg) = Left (intercalate " > " ctxs ++ ": " ++ msg) -eitherResult _ = Left "Result: incomplete input" diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/Buffer.hs b/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/Buffer.hs deleted file mode 100644 index ac94dfcc..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/Buffer.hs +++ /dev/null @@ -1,156 +0,0 @@ -{-# LANGUAGE BangPatterns #-} --- | --- Module : Data.Attoparsec.ByteString.Buffer --- Copyright : Bryan O'Sullivan 2007-2015 --- License : BSD3 --- --- Maintainer : bos@serpentine.com --- Stability : experimental --- Portability : GHC --- --- An "immutable" buffer that supports cheap appends. --- --- A Buffer is divided into an immutable read-only zone, followed by a --- mutable area that we've preallocated, but not yet written to. --- --- We overallocate at the end of a Buffer so that we can cheaply --- append. Since a user of an existing Buffer cannot see past the end --- of its immutable zone into the data that will change during an --- append, this is safe. --- --- Once we run out of space at the end of a Buffer, we do the usual --- doubling of the buffer size. --- --- The fact of having a mutable buffer really helps with performance, --- but it does have a consequence: if someone misuses the Partial API --- that attoparsec uses by calling the same continuation repeatedly --- (which never makes sense in practice), they could overwrite data. --- --- Since the API *looks* pure, it should *act* pure, too, so we use --- two generation counters (one mutable, one immutable) to track the --- number of appends to a mutable buffer. If the counters ever get out --- of sync, someone is appending twice to a mutable buffer, so we --- duplicate the entire buffer in order to preserve the immutability --- of its older self. --- --- While we could go a step further and gain protection against API --- abuse on a multicore system, by use of an atomic increment --- instruction to bump the mutable generation counter, that would be --- very expensive, and feels like it would also be in the realm of the --- ridiculous. Clients should never call a continuation more than --- once; we lack a linear type system that could enforce this; and --- there's only so far we should go to accommodate broken uses. - -module Data.Attoparsec.ByteString.Buffer - ( - Buffer - , buffer - , unbuffer - , pappend - , length - , unsafeIndex - , substring - , unsafeDrop - ) where - -import Control.Exception (assert) -import Data.ByteString.Internal (ByteString(..), memcpy, nullForeignPtr) -import Data.Attoparsec.Internal.Fhthagn (inlinePerformIO) -import Data.List (foldl1') -import Data.Monoid as Mon (Monoid(..)) -import Data.Semigroup (Semigroup(..)) -import Data.Word (Word8) -import Foreign.ForeignPtr (ForeignPtr, withForeignPtr) -import Foreign.Ptr (castPtr, plusPtr) -import Foreign.Storable (peek, peekByteOff, poke, sizeOf) -import GHC.ForeignPtr (mallocPlainForeignPtrBytes) -import Prelude hiding (length) - --- If _cap is zero, this buffer is empty. -data Buffer = Buf { - _fp :: {-# UNPACK #-} !(ForeignPtr Word8) - , _off :: {-# UNPACK #-} !Int - , _len :: {-# UNPACK #-} !Int - , _cap :: {-# UNPACK #-} !Int - , _gen :: {-# UNPACK #-} !Int - } - -instance Show Buffer where - showsPrec p = showsPrec p . unbuffer - --- | The initial 'Buffer' has no mutable zone, so we can avoid all --- copies in the (hopefully) common case of no further input being fed --- to us. -buffer :: ByteString -> Buffer -buffer (PS fp off len) = Buf fp off len len 0 - -unbuffer :: Buffer -> ByteString -unbuffer (Buf fp off len _ _) = PS fp off len - -instance Semigroup Buffer where - (Buf _ _ _ 0 _) <> b = b - a <> (Buf _ _ _ 0 _) = a - buf <> (Buf fp off len _ _) = append buf fp off len - -instance Monoid Buffer where - mempty = Buf nullForeignPtr 0 0 0 0 - - mappend = (<>) - - mconcat [] = Mon.mempty - mconcat xs = foldl1' mappend xs - -pappend :: Buffer -> ByteString -> Buffer -pappend (Buf _ _ _ 0 _) bs = buffer bs -pappend buf (PS fp off len) = append buf fp off len - -append :: Buffer -> ForeignPtr a -> Int -> Int -> Buffer -append (Buf fp0 off0 len0 cap0 gen0) !fp1 !off1 !len1 = - inlinePerformIO . withForeignPtr fp0 $ \ptr0 -> - withForeignPtr fp1 $ \ptr1 -> do - let genSize = sizeOf (0::Int) - newlen = len0 + len1 - gen <- if gen0 == 0 - then return 0 - else peek (castPtr ptr0) - if gen == gen0 && newlen <= cap0 - then do - let newgen = gen + 1 - poke (castPtr ptr0) newgen - memcpy (ptr0 `plusPtr` (off0+len0)) - (ptr1 `plusPtr` off1) - (fromIntegral len1) - return (Buf fp0 off0 newlen cap0 newgen) - else do - let newcap = newlen * 2 - fp <- mallocPlainForeignPtrBytes (newcap + genSize) - withForeignPtr fp $ \ptr_ -> do - let ptr = ptr_ `plusPtr` genSize - newgen = 1 - poke (castPtr ptr_) newgen - memcpy ptr (ptr0 `plusPtr` off0) (fromIntegral len0) - memcpy (ptr `plusPtr` len0) (ptr1 `plusPtr` off1) - (fromIntegral len1) - return (Buf fp genSize newlen newcap newgen) - -length :: Buffer -> Int -length (Buf _ _ len _ _) = len -{-# INLINE length #-} - -unsafeIndex :: Buffer -> Int -> Word8 -unsafeIndex (Buf fp off len _ _) i = assert (i >= 0 && i < len) . - inlinePerformIO . withForeignPtr fp $ flip peekByteOff (off+i) -{-# INLINE unsafeIndex #-} - -substring :: Int -> Int -> Buffer -> ByteString -substring s l (Buf fp off len _ _) = - assert (s >= 0 && s <= len) . - assert (l >= 0 && l <= len-s) $ - PS fp (off+s) l -{-# INLINE substring #-} - -unsafeDrop :: Int -> Buffer -> ByteString -unsafeDrop s (Buf fp off len _ _) = - assert (s >= 0 && s <= len) $ - PS fp (off+s) (len-s) -{-# INLINE unsafeDrop #-} diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/Char8.hs b/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/Char8.hs deleted file mode 100644 index 7fafba40..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/Char8.hs +++ /dev/null @@ -1,464 +0,0 @@ -{-# LANGUAGE BangPatterns, CPP, FlexibleInstances, TypeFamilies, - TypeSynonymInstances, GADTs #-} -#if __GLASGOW_HASKELL__ >= 702 -{-# LANGUAGE Trustworthy #-} -- Imports internal modules -#endif -{-# OPTIONS_GHC -fno-warn-orphans -fno-warn-warnings-deprecations #-} - --- | --- Module : Data.Attoparsec.ByteString.Char8 --- Copyright : Bryan O'Sullivan 2007-2015 --- License : BSD3 --- --- Maintainer : bos@serpentine.com --- Stability : experimental --- Portability : unknown --- --- Simple, efficient, character-oriented combinator parsing for --- 'B.ByteString' strings, loosely based on the Parsec library. - -module Data.Attoparsec.ByteString.Char8 - ( - -- * Character encodings - -- $encodings - - -- * Parser types - Parser - , A.Result - , A.IResult(..) - , I.compareResults - - -- * Running parsers - , A.parse - , A.feed - , A.parseOnly - , A.parseWith - , A.parseTest - - -- ** Result conversion - , A.maybeResult - , A.eitherResult - - -- * Parsing individual characters - , char - , char8 - , anyChar - , notChar - , satisfy - - -- ** Lookahead - , peekChar - , peekChar' - - -- ** Special character parsers - , digit - , letter_iso8859_15 - , letter_ascii - , space - - -- ** Fast predicates - , isDigit - , isDigit_w8 - , isAlpha_iso8859_15 - , isAlpha_ascii - , isSpace - , isSpace_w8 - - -- *** Character classes - , inClass - , notInClass - - -- * Efficient string handling - , I.string - , I.stringCI - , skipSpace - , skipWhile - , I.take - , scan - , takeWhile - , takeWhile1 - , takeTill - - -- ** String combinators - -- $specalt - , (.*>) - , (<*.) - - -- ** Consume all remaining input - , I.takeByteString - , I.takeLazyByteString - - -- * Text parsing - , I.endOfLine - , isEndOfLine - , isHorizontalSpace - - -- * Numeric parsers - , decimal - , hexadecimal - , signed - - -- * Combinators - , try - , (<?>) - , choice - , count - , option - , many' - , many1 - , many1' - , manyTill - , manyTill' - , sepBy - , sepBy' - , sepBy1 - , sepBy1' - , skipMany - , skipMany1 - , eitherP - , I.match - -- * State observation and manipulation functions - , I.endOfInput - , I.atEnd - ) where - -#if !MIN_VERSION_base(4,8,0) -import Control.Applicative (pure, (*>), (<*), (<$>)) -import Data.Word (Word) -#endif -import Control.Applicative ((<|>)) -import Data.Attoparsec.ByteString.FastSet (charClass, memberChar) -import Data.Attoparsec.ByteString.Internal (Parser) -import Data.Attoparsec.Combinator -import Data.Bits (Bits, (.|.), shiftL) -import Data.ByteString.Internal (c2w, w2c) -import Data.Int (Int8, Int16, Int32, Int64) -import Data.String (IsString(..)) -import Data.Word (Word8, Word16, Word32, Word64) -import Prelude hiding (takeWhile) -import qualified Data.Attoparsec.ByteString as A -import qualified Data.Attoparsec.ByteString.Internal as I -import qualified Data.Attoparsec.Internal as I -import qualified Data.ByteString as B8 -import qualified Data.ByteString.Char8 as B - -instance (a ~ B.ByteString) => IsString (Parser a) where - fromString = I.string . B.pack - --- $encodings --- --- This module is intended for parsing text that is --- represented using an 8-bit character set, e.g. ASCII or --- ISO-8859-15. It /does not/ make any attempt to deal with character --- encodings, multibyte characters, or wide characters. In --- particular, all attempts to use characters above code point U+00FF --- will give wrong answers. --- --- Code points below U+0100 are simply translated to and from their --- numeric values, so e.g. the code point U+00A4 becomes the byte --- @0xA4@ (which is the Euro symbol in ISO-8859-15, but the generic --- currency sign in ISO-8859-1). Haskell 'Char' values above U+00FF --- are truncated, so e.g. U+1D6B7 is truncated to the byte @0xB7@. - --- | Consume input as long as the predicate returns 'True', and return --- the consumed input. --- --- This parser requires the predicate to succeed on at least one byte --- of input: it will fail if the predicate never returns 'True' or if --- there is no input left. -takeWhile1 :: (Char -> Bool) -> Parser B.ByteString -takeWhile1 p = I.takeWhile1 (p . w2c) -{-# INLINE takeWhile1 #-} - --- | The parser @satisfy p@ succeeds for any byte for which the --- predicate @p@ returns 'True'. Returns the byte that is actually --- parsed. --- --- >digit = satisfy isDigit --- > where isDigit c = c >= '0' && c <= '9' -satisfy :: (Char -> Bool) -> Parser Char -satisfy = I.satisfyWith w2c -{-# INLINE satisfy #-} - --- | Match a letter, in the ISO-8859-15 encoding. -letter_iso8859_15 :: Parser Char -letter_iso8859_15 = satisfy isAlpha_iso8859_15 <?> "letter_iso8859_15" -{-# INLINE letter_iso8859_15 #-} - --- | Match a letter, in the ASCII encoding. -letter_ascii :: Parser Char -letter_ascii = satisfy isAlpha_ascii <?> "letter_ascii" -{-# INLINE letter_ascii #-} - --- | A fast alphabetic predicate for the ISO-8859-15 encoding --- --- /Note/: For all character encodings other than ISO-8859-15, and --- almost all Unicode code points above U+00A3, this predicate gives --- /wrong answers/. -isAlpha_iso8859_15 :: Char -> Bool -isAlpha_iso8859_15 c = (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z') || - (c >= '\166' && moby c) - where moby = notInClass "\167\169\171-\179\182\183\185\187\191\215\247" - {-# NOINLINE moby #-} -{-# INLINE isAlpha_iso8859_15 #-} - --- | A fast alphabetic predicate for the ASCII encoding --- --- /Note/: For all character encodings other than ASCII, and --- almost all Unicode code points above U+007F, this predicate gives --- /wrong answers/. -isAlpha_ascii :: Char -> Bool -isAlpha_ascii c = (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z') -{-# INLINE isAlpha_ascii #-} - --- | Parse a single digit. -digit :: Parser Char -digit = satisfy isDigit <?> "digit" -{-# INLINE digit #-} - --- | A fast digit predicate. -isDigit :: Char -> Bool -isDigit c = c >= '0' && c <= '9' -{-# INLINE isDigit #-} - --- | A fast digit predicate. -isDigit_w8 :: Word8 -> Bool -isDigit_w8 w = w - 48 <= 9 -{-# INLINE isDigit_w8 #-} - --- | Match any character. -anyChar :: Parser Char -anyChar = satisfy $ const True -{-# INLINE anyChar #-} - --- | Match any character, to perform lookahead. Returns 'Nothing' if --- end of input has been reached. Does not consume any input. --- --- /Note/: Because this parser does not fail, do not use it with --- combinators such as 'many', because such parsers loop until a --- failure occurs. Careless use will thus result in an infinite loop. -peekChar :: Parser (Maybe Char) -peekChar = (fmap w2c) `fmap` I.peekWord8 -{-# INLINE peekChar #-} - --- | Match any character, to perform lookahead. Does not consume any --- input, but will fail if end of input has been reached. -peekChar' :: Parser Char -peekChar' = w2c `fmap` I.peekWord8' -{-# INLINE peekChar' #-} - --- | Fast predicate for matching ASCII space characters. --- --- /Note/: This predicate only gives correct answers for the ASCII --- encoding. For instance, it does not recognise U+00A0 (non-breaking --- space) as a space character, even though it is a valid ISO-8859-15 --- byte. For a Unicode-aware and only slightly slower predicate, --- use 'Data.Char.isSpace' -isSpace :: Char -> Bool -isSpace c = (c == ' ') || ('\t' <= c && c <= '\r') -{-# INLINE isSpace #-} - --- | Fast 'Word8' predicate for matching ASCII space characters. -isSpace_w8 :: Word8 -> Bool -isSpace_w8 w = w == 32 || w - 9 <= 4 -{-# INLINE isSpace_w8 #-} - - --- | Parse a space character. --- --- /Note/: This parser only gives correct answers for the ASCII --- encoding. For instance, it does not recognise U+00A0 (non-breaking --- space) as a space character, even though it is a valid ISO-8859-15 --- byte. -space :: Parser Char -space = satisfy isSpace <?> "space" -{-# INLINE space #-} - --- | Match a specific character. -char :: Char -> Parser Char -char c = satisfy (== c) <?> [c] -{-# INLINE char #-} - --- | Match a specific character, but return its 'Word8' value. -char8 :: Char -> Parser Word8 -char8 c = I.satisfy (== c2w c) <?> [c] -{-# INLINE char8 #-} - --- | Match any character except the given one. -notChar :: Char -> Parser Char -notChar c = satisfy (/= c) <?> "not " ++ [c] -{-# INLINE notChar #-} - --- | Match any character in a set. --- --- >vowel = inClass "aeiou" --- --- Range notation is supported. --- --- >halfAlphabet = inClass "a-nA-N" --- --- To add a literal \'-\' to a set, place it at the beginning or end --- of the string. -inClass :: String -> Char -> Bool -inClass s = (`memberChar` mySet) - where mySet = charClass s -{-# INLINE inClass #-} - --- | Match any character not in a set. -notInClass :: String -> Char -> Bool -notInClass s = not . inClass s -{-# INLINE notInClass #-} - --- | Consume input as long as the predicate returns 'True', and return --- the consumed input. --- --- This parser does not fail. It will return an empty string if the --- predicate returns 'False' on the first byte of input. --- --- /Note/: Because this parser does not fail, do not use it with --- combinators such as 'many', because such parsers loop until a --- failure occurs. Careless use will thus result in an infinite loop. -takeWhile :: (Char -> Bool) -> Parser B.ByteString -takeWhile p = I.takeWhile (p . w2c) -{-# INLINE takeWhile #-} - --- | A stateful scanner. The predicate consumes and transforms a --- state argument, and each transformed state is passed to successive --- invocations of the predicate on each byte of the input until one --- returns 'Nothing' or the input ends. --- --- This parser does not fail. It will return an empty string if the --- predicate returns 'Nothing' on the first byte of input. --- --- /Note/: Because this parser does not fail, do not use it with --- combinators such as 'many', because such parsers loop until a --- failure occurs. Careless use will thus result in an infinite loop. -scan :: s -> (s -> Char -> Maybe s) -> Parser B.ByteString -scan s0 p = I.scan s0 (\s -> p s . w2c) -{-# INLINE scan #-} - --- | Consume input as long as the predicate returns 'False' --- (i.e. until it returns 'True'), and return the consumed input. --- --- This parser does not fail. It will return an empty string if the --- predicate returns 'True' on the first byte of input. --- --- /Note/: Because this parser does not fail, do not use it with --- combinators such as 'many', because such parsers loop until a --- failure occurs. Careless use will thus result in an infinite loop. -takeTill :: (Char -> Bool) -> Parser B.ByteString -takeTill p = I.takeTill (p . w2c) -{-# INLINE takeTill #-} - --- | Skip past input for as long as the predicate returns 'True'. -skipWhile :: (Char -> Bool) -> Parser () -skipWhile p = I.skipWhile (p . w2c) -{-# INLINE skipWhile #-} - --- | Skip over white space. -skipSpace :: Parser () -skipSpace = I.skipWhile isSpace_w8 -{-# INLINE skipSpace #-} - --- $specalt --- --- If you enable the @OverloadedStrings@ language extension, you can --- use the '*>' and '<*' combinators to simplify the common task of --- matching a statically known string, then immediately parsing --- something else. --- --- Instead of writing something like this: --- --- @ ---'I.string' \"foo\" '*>' wibble --- @ --- --- Using @OverloadedStrings@, you can omit the explicit use of --- 'I.string', and write a more compact version: --- --- @ --- \"foo\" '*>' wibble --- @ --- --- (Note: the '.*>' and '<*.' combinators that were originally --- provided for this purpose are obsolete and unnecessary, and will be --- removed in the next major version.) - --- | /Obsolete/. A type-specialized version of '*>' for --- 'B.ByteString'. Use '*>' instead. -(.*>) :: B.ByteString -> Parser a -> Parser a -s .*> f = I.string s *> f -{-# DEPRECATED (.*>) "This is no longer necessary, and will be removed. Use '*>' instead." #-} - --- | /Obsolete/. A type-specialized version of '<*' for --- 'B.ByteString'. Use '<*' instead. -(<*.) :: Parser a -> B.ByteString -> Parser a -f <*. s = f <* I.string s -{-# DEPRECATED (<*.) "This is no longer necessary, and will be removed. Use '<*' instead." #-} - --- | A predicate that matches either a carriage return @\'\\r\'@ or --- newline @\'\\n\'@ character. -isEndOfLine :: Word8 -> Bool -isEndOfLine w = w == 13 || w == 10 -{-# INLINE isEndOfLine #-} - --- | A predicate that matches either a space @\' \'@ or horizontal tab --- @\'\\t\'@ character. -isHorizontalSpace :: Word8 -> Bool -isHorizontalSpace w = w == 32 || w == 9 -{-# INLINE isHorizontalSpace #-} - --- | Parse and decode an unsigned hexadecimal number. The hex digits --- @\'a\'@ through @\'f\'@ may be upper or lower case. --- --- This parser does not accept a leading @\"0x\"@ string. -hexadecimal :: (Integral a, Bits a) => Parser a -hexadecimal = B8.foldl' step 0 `fmap` I.takeWhile1 isHexDigit - where - isHexDigit w = (w >= 48 && w <= 57) || - (w >= 97 && w <= 102) || - (w >= 65 && w <= 70) - step a w | w >= 48 && w <= 57 = (a `shiftL` 4) .|. fromIntegral (w - 48) - | w >= 97 = (a `shiftL` 4) .|. fromIntegral (w - 87) - | otherwise = (a `shiftL` 4) .|. fromIntegral (w - 55) -{-# SPECIALISE hexadecimal :: Parser Int #-} -{-# SPECIALISE hexadecimal :: Parser Int8 #-} -{-# SPECIALISE hexadecimal :: Parser Int16 #-} -{-# SPECIALISE hexadecimal :: Parser Int32 #-} -{-# SPECIALISE hexadecimal :: Parser Int64 #-} -{-# SPECIALISE hexadecimal :: Parser Integer #-} -{-# SPECIALISE hexadecimal :: Parser Word #-} -{-# SPECIALISE hexadecimal :: Parser Word8 #-} -{-# SPECIALISE hexadecimal :: Parser Word16 #-} -{-# SPECIALISE hexadecimal :: Parser Word32 #-} -{-# SPECIALISE hexadecimal :: Parser Word64 #-} - --- | Parse and decode an unsigned decimal number. -decimal :: Integral a => Parser a -decimal = B8.foldl' step 0 `fmap` I.takeWhile1 isDigit_w8 - where step a w = a * 10 + fromIntegral (w - 48) -{-# SPECIALISE decimal :: Parser Int #-} -{-# SPECIALISE decimal :: Parser Int8 #-} -{-# SPECIALISE decimal :: Parser Int16 #-} -{-# SPECIALISE decimal :: Parser Int32 #-} -{-# SPECIALISE decimal :: Parser Int64 #-} -{-# SPECIALISE decimal :: Parser Integer #-} -{-# SPECIALISE decimal :: Parser Word #-} -{-# SPECIALISE decimal :: Parser Word8 #-} -{-# SPECIALISE decimal :: Parser Word16 #-} -{-# SPECIALISE decimal :: Parser Word32 #-} -{-# SPECIALISE decimal :: Parser Word64 #-} - --- | Parse a number with an optional leading @\'+\'@ or @\'-\'@ sign --- character. -signed :: Num a => Parser a -> Parser a -{-# SPECIALISE signed :: Parser Int -> Parser Int #-} -{-# SPECIALISE signed :: Parser Int8 -> Parser Int8 #-} -{-# SPECIALISE signed :: Parser Int16 -> Parser Int16 #-} -{-# SPECIALISE signed :: Parser Int32 -> Parser Int32 #-} -{-# SPECIALISE signed :: Parser Int64 -> Parser Int64 #-} -{-# SPECIALISE signed :: Parser Integer -> Parser Integer #-} -signed p = (negate <$> (char8 '-' *> p)) - <|> (char8 '+' *> p) - <|> p - diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/FastSet.hs b/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/FastSet.hs deleted file mode 100644 index d15854c4..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/FastSet.hs +++ /dev/null @@ -1,115 +0,0 @@ -{-# LANGUAGE BangPatterns, MagicHash #-} - ------------------------------------------------------------------------------ --- | --- Module : Data.Attoparsec.ByteString.FastSet --- Copyright : Bryan O'Sullivan 2007-2015 --- License : BSD3 --- --- Maintainer : bos@serpentine.com --- Stability : experimental --- Portability : unknown --- --- Fast set membership tests for 'Word8' and 8-bit 'Char' values. The --- set representation is unboxed for efficiency. For small sets, we --- test for membership using a binary search. For larger sets, we use --- a lookup table. --- ------------------------------------------------------------------------------ -module Data.Attoparsec.ByteString.FastSet - ( - -- * Data type - FastSet - -- * Construction - , fromList - , set - -- * Lookup - , memberChar - , memberWord8 - -- * Debugging - , fromSet - -- * Handy interface - , charClass - ) where - -import Data.Bits ((.&.), (.|.)) -import Foreign.Storable (peekByteOff, pokeByteOff) -import GHC.Base (Int(I#), iShiftRA#, narrow8Word#, shiftL#) -import GHC.Word (Word8(W8#)) -import qualified Data.ByteString as B -import qualified Data.ByteString.Char8 as B8 -import qualified Data.ByteString.Internal as I -import qualified Data.ByteString.Unsafe as U - -data FastSet = Sorted { fromSet :: !B.ByteString } - | Table { fromSet :: !B.ByteString } - deriving (Eq, Ord) - -instance Show FastSet where - show (Sorted s) = "FastSet Sorted " ++ show (B8.unpack s) - show (Table _) = "FastSet Table" - --- | The lower bound on the size of a lookup table. We choose this to --- balance table density against performance. -tableCutoff :: Int -tableCutoff = 8 - --- | Create a set. -set :: B.ByteString -> FastSet -set s | B.length s < tableCutoff = Sorted . B.sort $ s - | otherwise = Table . mkTable $ s - -fromList :: [Word8] -> FastSet -fromList = set . B.pack - -data I = I {-# UNPACK #-} !Int {-# UNPACK #-} !Word8 - -shiftR :: Int -> Int -> Int -shiftR (I# x#) (I# i#) = I# (x# `iShiftRA#` i#) - -shiftL :: Word8 -> Int -> Word8 -shiftL (W8# x#) (I# i#) = W8# (narrow8Word# (x# `shiftL#` i#)) - -index :: Int -> I -index i = I (i `shiftR` 3) (1 `shiftL` (i .&. 7)) -{-# INLINE index #-} - --- | Check the set for membership. -memberWord8 :: Word8 -> FastSet -> Bool -memberWord8 w (Table t) = - let I byte bit = index (fromIntegral w) - in U.unsafeIndex t byte .&. bit /= 0 -memberWord8 w (Sorted s) = search 0 (B.length s - 1) - where search lo hi - | hi < lo = False - | otherwise = - let mid = (lo + hi) `quot` 2 - in case compare w (U.unsafeIndex s mid) of - GT -> search (mid + 1) hi - LT -> search lo (mid - 1) - _ -> True - --- | Check the set for membership. Only works with 8-bit characters: --- characters above code point 255 will give wrong answers. -memberChar :: Char -> FastSet -> Bool -memberChar c = memberWord8 (I.c2w c) -{-# INLINE memberChar #-} - -mkTable :: B.ByteString -> B.ByteString -mkTable s = I.unsafeCreate 32 $ \t -> do - _ <- I.memset t 0 32 - U.unsafeUseAsCStringLen s $ \(p, l) -> - let loop n | n == l = return () - | otherwise = do - c <- peekByteOff p n :: IO Word8 - let I byte bit = index (fromIntegral c) - prev <- peekByteOff t byte :: IO Word8 - pokeByteOff t byte (prev .|. bit) - loop (n + 1) - in loop 0 - -charClass :: String -> FastSet -charClass = set . B8.pack . go - where go (a:'-':b:xs) = [a..b] ++ go xs - go (x:xs) = x : go xs - go _ = "" diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/Internal.hs b/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/Internal.hs deleted file mode 100644 index 4938ea87..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/ByteString/Internal.hs +++ /dev/null @@ -1,536 +0,0 @@ -{-# LANGUAGE BangPatterns, CPP, GADTs, OverloadedStrings, RankNTypes, - RecordWildCards #-} --- | --- Module : Data.Attoparsec.ByteString.Internal --- Copyright : Bryan O'Sullivan 2007-2015 --- License : BSD3 --- --- Maintainer : bos@serpentine.com --- Stability : experimental --- Portability : unknown --- --- Simple, efficient parser combinators for 'ByteString' strings, --- loosely based on the Parsec library. - -module Data.Attoparsec.ByteString.Internal - ( - -- * Parser types - Parser - , Result - - -- * Running parsers - , parse - , parseOnly - - -- * Combinators - , module Data.Attoparsec.Combinator - - -- * Parsing individual bytes - , satisfy - , satisfyWith - , anyWord8 - , skip - , word8 - , notWord8 - - -- ** Lookahead - , peekWord8 - , peekWord8' - - -- ** Byte classes - , inClass - , notInClass - - -- * Parsing more complicated structures - , storable - - -- * Efficient string handling - , skipWhile - , string - , stringCI - , take - , scan - , runScanner - , takeWhile - , takeWhile1 - , takeTill - - -- ** Consume all remaining input - , takeByteString - , takeLazyByteString - - -- * Utilities - , endOfLine - , endOfInput - , match - , atEnd - ) where - -#if !MIN_VERSION_base(4,8,0) -import Control.Applicative ((<$>)) -#endif -import Control.Applicative ((<|>)) -import Control.Monad (when) -import Data.Attoparsec.ByteString.Buffer (Buffer, buffer) -import Data.Attoparsec.ByteString.FastSet (charClass, memberWord8) -import Data.Attoparsec.Combinator ((<?>)) -import Data.Attoparsec.Internal -import Data.Attoparsec.Internal.Fhthagn (inlinePerformIO) -import Data.Attoparsec.Internal.Types hiding (Parser, Failure, Success) -import Data.ByteString (ByteString) -import Data.List (intercalate) -import Data.Word (Word8) -import Foreign.ForeignPtr (withForeignPtr) -import Foreign.Ptr (castPtr, minusPtr, plusPtr) -import Foreign.Storable (Storable(peek, sizeOf)) -import Prelude hiding (getChar, succ, take, takeWhile) -import qualified Data.Attoparsec.ByteString.Buffer as Buf -import qualified Data.Attoparsec.Internal.Types as T -import qualified Data.ByteString as B8 -import qualified Data.ByteString.Char8 as B -import qualified Data.ByteString.Internal as B -import qualified Data.ByteString.Lazy as L -import qualified Data.ByteString.Unsafe as B - -type Parser = T.Parser ByteString -type Result = IResult ByteString -type Failure r = T.Failure ByteString Buffer r -type Success a r = T.Success ByteString Buffer a r - --- | The parser @satisfy p@ succeeds for any byte for which the --- predicate @p@ returns 'True'. Returns the byte that is actually --- parsed. --- --- >digit = satisfy isDigit --- > where isDigit w = w >= 48 && w <= 57 -satisfy :: (Word8 -> Bool) -> Parser Word8 -satisfy p = do - h <- peekWord8' - if p h - then advance 1 >> return h - else fail "satisfy" -{-# INLINE satisfy #-} - --- | The parser @skip p@ succeeds for any byte for which the predicate --- @p@ returns 'True'. --- --- >skipDigit = skip isDigit --- > where isDigit w = w >= 48 && w <= 57 -skip :: (Word8 -> Bool) -> Parser () -skip p = do - h <- peekWord8' - if p h - then advance 1 - else fail "skip" - --- | The parser @satisfyWith f p@ transforms a byte, and succeeds if --- the predicate @p@ returns 'True' on the transformed value. The --- parser returns the transformed byte that was parsed. -satisfyWith :: (Word8 -> a) -> (a -> Bool) -> Parser a -satisfyWith f p = do - h <- peekWord8' - let c = f h - if p c - then advance 1 >> return c - else fail "satisfyWith" -{-# INLINE satisfyWith #-} - -storable :: Storable a => Parser a -storable = hack undefined - where - hack :: Storable b => b -> Parser b - hack dummy = do - (fp,o,_) <- B.toForeignPtr `fmap` take (sizeOf dummy) - return . inlinePerformIO . withForeignPtr fp $ \p -> - peek (castPtr $ p `plusPtr` o) - --- | Consume exactly @n@ bytes of input. -take :: Int -> Parser ByteString -take n0 = do - let n = max n0 0 - s <- ensure n - advance n >> return s -{-# INLINE take #-} - --- | @string s@ parses a sequence of bytes that identically match --- @s@. Returns the parsed string (i.e. @s@). This parser consumes no --- input if it fails (even if a partial match). --- --- /Note/: The behaviour of this parser is different to that of the --- similarly-named parser in Parsec, as this one is all-or-nothing. --- To illustrate the difference, the following parser will fail under --- Parsec given an input of @\"for\"@: --- --- >string "foo" <|> string "for" --- --- The reason for its failure is that the first branch is a --- partial match, and will consume the letters @\'f\'@ and @\'o\'@ --- before failing. In attoparsec, the above parser will /succeed/ on --- that input, because the failed first branch will consume nothing. -string :: ByteString -> Parser ByteString -string s = string_ (stringSuspended id) id s -{-# INLINE string #-} - --- ASCII-specific but fast, oh yes. -toLower :: Word8 -> Word8 -toLower w | w >= 65 && w <= 90 = w + 32 - | otherwise = w - --- | Satisfy a literal string, ignoring case. -stringCI :: ByteString -> Parser ByteString -stringCI s = string_ (stringSuspended lower) lower s - where lower = B8.map toLower -{-# INLINE stringCI #-} - -string_ :: (forall r. ByteString -> ByteString -> Buffer -> Pos -> More - -> Failure r -> Success ByteString r -> Result r) - -> (ByteString -> ByteString) - -> ByteString -> Parser ByteString -string_ suspended f s0 = T.Parser $ \t pos more lose succ -> - let n = B.length s - s = f s0 - in if lengthAtLeast pos n t - then let t' = substring pos (Pos n) t - in if s == f t' - then succ t (pos + Pos n) more t' - else lose t pos more [] "string" - else let t' = Buf.unsafeDrop (fromPos pos) t - in if f t' `B.isPrefixOf` s - then suspended s (B.drop (B.length t') s) t pos more lose succ - else lose t pos more [] "string" -{-# INLINE string_ #-} - -stringSuspended :: (ByteString -> ByteString) - -> ByteString -> ByteString -> Buffer -> Pos -> More - -> Failure r - -> Success ByteString r - -> Result r -stringSuspended f s0 s t pos more lose succ = - runParser (demandInput_ >>= go) t pos more lose succ - where go s'0 = T.Parser $ \t' pos' more' lose' succ' -> - let m = B.length s - s' = f s'0 - n = B.length s' - in if n >= m - then if B.unsafeTake m s' == s - then let o = Pos (B.length s0) - in succ' t' (pos' + o) more' - (substring pos' o t') - else lose' t' pos' more' [] "string" - else if s' == B.unsafeTake n s - then stringSuspended f s0 (B.unsafeDrop n s) - t' pos' more' lose' succ' - else lose' t' pos' more' [] "string" - --- | Skip past input for as long as the predicate returns 'True'. -skipWhile :: (Word8 -> Bool) -> Parser () -skipWhile p = go - where - go = do - t <- B8.takeWhile p <$> get - continue <- inputSpansChunks (B.length t) - when continue go -{-# INLINE skipWhile #-} - --- | Consume input as long as the predicate returns 'False' --- (i.e. until it returns 'True'), and return the consumed input. --- --- This parser does not fail. It will return an empty string if the --- predicate returns 'True' on the first byte of input. --- --- /Note/: Because this parser does not fail, do not use it with --- combinators such as 'Control.Applicative.many', because such --- parsers loop until a failure occurs. Careless use will thus result --- in an infinite loop. -takeTill :: (Word8 -> Bool) -> Parser ByteString -takeTill p = takeWhile (not . p) -{-# INLINE takeTill #-} - --- | Consume input as long as the predicate returns 'True', and return --- the consumed input. --- --- This parser does not fail. It will return an empty string if the --- predicate returns 'False' on the first byte of input. --- --- /Note/: Because this parser does not fail, do not use it with --- combinators such as 'Control.Applicative.many', because such --- parsers loop until a failure occurs. Careless use will thus result --- in an infinite loop. -takeWhile :: (Word8 -> Bool) -> Parser ByteString -takeWhile p = do - s <- B8.takeWhile p <$> get - continue <- inputSpansChunks (B.length s) - if continue - then takeWhileAcc p [s] - else return s -{-# INLINE takeWhile #-} - -takeWhileAcc :: (Word8 -> Bool) -> [ByteString] -> Parser ByteString -takeWhileAcc p = go - where - go acc = do - s <- B8.takeWhile p <$> get - continue <- inputSpansChunks (B.length s) - if continue - then go (s:acc) - else return $ concatReverse (s:acc) -{-# INLINE takeWhileAcc #-} - -takeRest :: Parser [ByteString] -takeRest = go [] - where - go acc = do - input <- wantInput - if input - then do - s <- get - advance (B.length s) - go (s:acc) - else return (reverse acc) - --- | Consume all remaining input and return it as a single string. -takeByteString :: Parser ByteString -takeByteString = B.concat `fmap` takeRest - --- | Consume all remaining input and return it as a single string. -takeLazyByteString :: Parser L.ByteString -takeLazyByteString = L.fromChunks `fmap` takeRest - -data T s = T {-# UNPACK #-} !Int s - -scan_ :: (s -> [ByteString] -> Parser r) -> s -> (s -> Word8 -> Maybe s) - -> Parser r -scan_ f s0 p = go [] s0 - where - go acc s1 = do - let scanner (B.PS fp off len) = - withForeignPtr fp $ \ptr0 -> do - let start = ptr0 `plusPtr` off - end = start `plusPtr` len - inner ptr !s - | ptr < end = do - w <- peek ptr - case p s w of - Just s' -> inner (ptr `plusPtr` 1) s' - _ -> done (ptr `minusPtr` start) s - | otherwise = done (ptr `minusPtr` start) s - done !i !s = return (T i s) - inner start s1 - bs <- get - let T i s' = inlinePerformIO $ scanner bs - !h = B.unsafeTake i bs - continue <- inputSpansChunks i - if continue - then go (h:acc) s' - else f s' (h:acc) -{-# INLINE scan_ #-} - --- | A stateful scanner. The predicate consumes and transforms a --- state argument, and each transformed state is passed to successive --- invocations of the predicate on each byte of the input until one --- returns 'Nothing' or the input ends. --- --- This parser does not fail. It will return an empty string if the --- predicate returns 'Nothing' on the first byte of input. --- --- /Note/: Because this parser does not fail, do not use it with --- combinators such as 'Control.Applicative.many', because such --- parsers loop until a failure occurs. Careless use will thus result --- in an infinite loop. -scan :: s -> (s -> Word8 -> Maybe s) -> Parser ByteString -scan = scan_ $ \_ chunks -> return $! concatReverse chunks -{-# INLINE scan #-} - --- | Like 'scan', but generalized to return the final state of the --- scanner. -runScanner :: s -> (s -> Word8 -> Maybe s) -> Parser (ByteString, s) -runScanner = scan_ $ \s xs -> let !sx = concatReverse xs in return (sx, s) -{-# INLINE runScanner #-} - --- | Consume input as long as the predicate returns 'True', and return --- the consumed input. --- --- This parser requires the predicate to succeed on at least one byte --- of input: it will fail if the predicate never returns 'True' or if --- there is no input left. -takeWhile1 :: (Word8 -> Bool) -> Parser ByteString -takeWhile1 p = do - (`when` demandInput) =<< endOfChunk - s <- B8.takeWhile p <$> get - let len = B.length s - if len == 0 - then fail "takeWhile1" - else do - advance len - eoc <- endOfChunk - if eoc - then takeWhileAcc p [s] - else return s -{-# INLINE takeWhile1 #-} - --- | Match any byte in a set. --- --- >vowel = inClass "aeiou" --- --- Range notation is supported. --- --- >halfAlphabet = inClass "a-nA-N" --- --- To add a literal @\'-\'@ to a set, place it at the beginning or end --- of the string. -inClass :: String -> Word8 -> Bool -inClass s = (`memberWord8` mySet) - where mySet = charClass s - {-# NOINLINE mySet #-} -{-# INLINE inClass #-} - --- | Match any byte not in a set. -notInClass :: String -> Word8 -> Bool -notInClass s = not . inClass s -{-# INLINE notInClass #-} - --- | Match any byte. -anyWord8 :: Parser Word8 -anyWord8 = satisfy $ const True -{-# INLINE anyWord8 #-} - --- | Match a specific byte. -word8 :: Word8 -> Parser Word8 -word8 c = satisfy (== c) <?> show c -{-# INLINE word8 #-} - --- | Match any byte except the given one. -notWord8 :: Word8 -> Parser Word8 -notWord8 c = satisfy (/= c) <?> "not " ++ show c -{-# INLINE notWord8 #-} - --- | Match any byte, to perform lookahead. Returns 'Nothing' if end of --- input has been reached. Does not consume any input. --- --- /Note/: Because this parser does not fail, do not use it with --- combinators such as 'Control.Applicative.many', because such --- parsers loop until a failure occurs. Careless use will thus result --- in an infinite loop. -peekWord8 :: Parser (Maybe Word8) -peekWord8 = T.Parser $ \t pos@(Pos pos_) more _lose succ -> - case () of - _| pos_ < Buf.length t -> - let !w = Buf.unsafeIndex t pos_ - in succ t pos more (Just w) - | more == Complete -> - succ t pos more Nothing - | otherwise -> - let succ' t' pos' more' = let !w = Buf.unsafeIndex t' pos_ - in succ t' pos' more' (Just w) - lose' t' pos' more' = succ t' pos' more' Nothing - in prompt t pos more lose' succ' -{-# INLINE peekWord8 #-} - --- | Match any byte, to perform lookahead. Does not consume any --- input, but will fail if end of input has been reached. -peekWord8' :: Parser Word8 -peekWord8' = T.Parser $ \t pos more lose succ -> - if lengthAtLeast pos 1 t - then succ t pos more (Buf.unsafeIndex t (fromPos pos)) - else let succ' t' pos' more' bs' = succ t' pos' more' $! B.unsafeHead bs' - in ensureSuspended 1 t pos more lose succ' -{-# INLINE peekWord8' #-} - --- | Match either a single newline character @\'\\n\'@, or a carriage --- return followed by a newline character @\"\\r\\n\"@. -endOfLine :: Parser () -endOfLine = (word8 10 >> return ()) <|> (string "\r\n" >> return ()) - --- | Terminal failure continuation. -failK :: Failure a -failK t (Pos pos) _more stack msg = Fail (Buf.unsafeDrop pos t) stack msg -{-# INLINE failK #-} - --- | Terminal success continuation. -successK :: Success a a -successK t (Pos pos) _more a = Done (Buf.unsafeDrop pos t) a -{-# INLINE successK #-} - --- | Run a parser. -parse :: Parser a -> ByteString -> Result a -parse m s = T.runParser m (buffer s) (Pos 0) Incomplete failK successK -{-# INLINE parse #-} - --- | Run a parser that cannot be resupplied via a 'Partial' result. --- --- This function does not force a parser to consume all of its input. --- Instead, any residual input will be discarded. To force a parser --- to consume all of its input, use something like this: --- --- @ ---'parseOnly' (myParser 'Control.Applicative.<*' 'endOfInput') --- @ -parseOnly :: Parser a -> ByteString -> Either String a -parseOnly m s = case T.runParser m (buffer s) (Pos 0) Complete failK successK of - Fail _ [] err -> Left err - Fail _ ctxs err -> Left (intercalate " > " ctxs ++ ": " ++ err) - Done _ a -> Right a - _ -> error "parseOnly: impossible error!" -{-# INLINE parseOnly #-} - -get :: Parser ByteString -get = T.Parser $ \t pos more _lose succ -> - succ t pos more (Buf.unsafeDrop (fromPos pos) t) -{-# INLINE get #-} - -endOfChunk :: Parser Bool -endOfChunk = T.Parser $ \t pos more _lose succ -> - succ t pos more (fromPos pos == Buf.length t) -{-# INLINE endOfChunk #-} - -inputSpansChunks :: Int -> Parser Bool -inputSpansChunks i = T.Parser $ \t pos_ more _lose succ -> - let pos = pos_ + Pos i - in if fromPos pos < Buf.length t || more == Complete - then succ t pos more False - else let lose' t' pos' more' = succ t' pos' more' False - succ' t' pos' more' = succ t' pos' more' True - in prompt t pos more lose' succ' -{-# INLINE inputSpansChunks #-} - -advance :: Int -> Parser () -advance n = T.Parser $ \t pos more _lose succ -> - succ t (pos + Pos n) more () -{-# INLINE advance #-} - -ensureSuspended :: Int -> Buffer -> Pos -> More - -> Failure r - -> Success ByteString r - -> Result r -ensureSuspended n t pos more lose succ = - runParser (demandInput >> go) t pos more lose succ - where go = T.Parser $ \t' pos' more' lose' succ' -> - if lengthAtLeast pos' n t' - then succ' t' pos' more' (substring pos (Pos n) t') - else runParser (demandInput >> go) t' pos' more' lose' succ' - --- | If at least @n@ elements of input are available, return the --- current input, otherwise fail. -ensure :: Int -> Parser ByteString -ensure n = T.Parser $ \t pos more lose succ -> - if lengthAtLeast pos n t - then succ t pos more (substring pos (Pos n) t) - -- The uncommon case is kept out-of-line to reduce code size: - else ensureSuspended n t pos more lose succ -{-# INLINE ensure #-} - --- | Return both the result of a parse and the portion of the input --- that was consumed while it was being parsed. -match :: Parser a -> Parser (ByteString, a) -match p = T.Parser $ \t pos more lose succ -> - let succ' t' pos' more' a = - succ t' pos' more' (substring pos (pos'-pos) t', a) - in runParser p t pos more lose succ' - -lengthAtLeast :: Pos -> Int -> Buffer -> Bool -lengthAtLeast (Pos pos) n bs = Buf.length bs >= pos + n -{-# INLINE lengthAtLeast #-} - -substring :: Pos -> Pos -> Buffer -> ByteString -substring (Pos pos) (Pos n) = Buf.substring pos n -{-# INLINE substring #-} diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Combinator.hs b/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Combinator.hs deleted file mode 100644 index dde0c27a..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Combinator.hs +++ /dev/null @@ -1,233 +0,0 @@ -{-# LANGUAGE BangPatterns, CPP #-} -#if __GLASGOW_HASKELL__ >= 702 -{-# LANGUAGE Trustworthy #-} -- Imports internal modules -#endif --- | --- Module : Data.Attoparsec.Combinator --- Copyright : Daan Leijen 1999-2001, Bryan O'Sullivan 2007-2015 --- License : BSD3 --- --- Maintainer : bos@serpentine.com --- Stability : experimental --- Portability : portable --- --- Useful parser combinators, similar to those provided by Parsec. -module Data.Attoparsec.Combinator - ( - -- * Combinators - try - , (<?>) - , choice - , count - , option - , many' - , many1 - , many1' - , manyTill - , manyTill' - , sepBy - , sepBy' - , sepBy1 - , sepBy1' - , skipMany - , skipMany1 - , eitherP - , feed - , satisfyElem - , endOfInput - , atEnd - , lookAhead - ) where - -#if !MIN_VERSION_base(4,8,0) -import Control.Applicative (Applicative(..), (<$>)) -import Data.Monoid (Monoid(mappend)) -#endif -import Control.Applicative (Alternative(..), empty, liftA2, many, (<|>)) -import Control.Monad (MonadPlus(..)) -import Data.Attoparsec.Internal.Types (Parser(..), IResult(..)) -import Data.Attoparsec.Internal (endOfInput, atEnd, satisfyElem) -import Data.ByteString (ByteString) -import Prelude hiding (succ) - --- | Attempt a parse, and if it fails, rewind the input so that no --- input appears to have been consumed. --- --- This combinator is provided for compatibility with Parsec. --- attoparsec parsers always backtrack on failure. -try :: Parser i a -> Parser i a -try p = p -{-# INLINE try #-} - --- | Name the parser, in case failure occurs. -(<?>) :: Parser i a - -> String -- ^ the name to use if parsing fails - -> Parser i a -p <?> msg0 = Parser $ \t pos more lose succ -> - let lose' t' pos' more' strs msg = lose t' pos' more' (msg0:strs) msg - in runParser p t pos more lose' succ -{-# INLINE (<?>) #-} -infix 0 <?> - --- | @choice ps@ tries to apply the actions in the list @ps@ in order, --- until one of them succeeds. Returns the value of the succeeding --- action. -choice :: Alternative f => [f a] -> f a -choice = foldr (<|>) empty -{-# SPECIALIZE choice :: [Parser ByteString a] - -> Parser ByteString a #-} - --- | @option x p@ tries to apply action @p@. If @p@ fails without --- consuming input, it returns the value @x@, otherwise the value --- returned by @p@. --- --- > priority = option 0 (digitToInt <$> digit) -option :: Alternative f => a -> f a -> f a -option x p = p <|> pure x -{-# SPECIALIZE option :: a -> Parser ByteString a -> Parser ByteString a #-} - --- | A version of 'liftM2' that is strict in the result of its first --- action. -liftM2' :: (Monad m) => (a -> b -> c) -> m a -> m b -> m c -liftM2' f a b = do - !x <- a - y <- b - return (f x y) -{-# INLINE liftM2' #-} - --- | @many' p@ applies the action @p@ /zero/ or more times. Returns a --- list of the returned values of @p@. The value returned by @p@ is --- forced to WHNF. --- --- > word = many' letter -many' :: (MonadPlus m) => m a -> m [a] -many' p = many_p - where many_p = some_p `mplus` return [] - some_p = liftM2' (:) p many_p -{-# INLINE many' #-} - --- | @many1 p@ applies the action @p@ /one/ or more times. Returns a --- list of the returned values of @p@. --- --- > word = many1 letter -many1 :: Alternative f => f a -> f [a] -many1 p = liftA2 (:) p (many p) -{-# INLINE many1 #-} - --- | @many1' p@ applies the action @p@ /one/ or more times. Returns a --- list of the returned values of @p@. The value returned by @p@ is --- forced to WHNF. --- --- > word = many1' letter -many1' :: (MonadPlus m) => m a -> m [a] -many1' p = liftM2' (:) p (many' p) -{-# INLINE many1' #-} - --- | @sepBy p sep@ applies /zero/ or more occurrences of @p@, separated --- by @sep@. Returns a list of the values returned by @p@. --- --- > commaSep p = p `sepBy` (char ',') -sepBy :: Alternative f => f a -> f s -> f [a] -sepBy p s = liftA2 (:) p ((s *> sepBy1 p s) <|> pure []) <|> pure [] -{-# SPECIALIZE sepBy :: Parser ByteString a -> Parser ByteString s - -> Parser ByteString [a] #-} - --- | @sepBy' p sep@ applies /zero/ or more occurrences of @p@, separated --- by @sep@. Returns a list of the values returned by @p@. The value --- returned by @p@ is forced to WHNF. --- --- > commaSep p = p `sepBy'` (char ',') -sepBy' :: (MonadPlus m) => m a -> m s -> m [a] -sepBy' p s = scan `mplus` return [] - where scan = liftM2' (:) p ((s >> sepBy1' p s) `mplus` return []) -{-# SPECIALIZE sepBy' :: Parser ByteString a -> Parser ByteString s - -> Parser ByteString [a] #-} - --- | @sepBy1 p sep@ applies /one/ or more occurrences of @p@, separated --- by @sep@. Returns a list of the values returned by @p@. --- --- > commaSep p = p `sepBy1` (char ',') -sepBy1 :: Alternative f => f a -> f s -> f [a] -sepBy1 p s = scan - where scan = liftA2 (:) p ((s *> scan) <|> pure []) -{-# SPECIALIZE sepBy1 :: Parser ByteString a -> Parser ByteString s - -> Parser ByteString [a] #-} - --- | @sepBy1' p sep@ applies /one/ or more occurrences of @p@, separated --- by @sep@. Returns a list of the values returned by @p@. The value --- returned by @p@ is forced to WHNF. --- --- > commaSep p = p `sepBy1'` (char ',') -sepBy1' :: (MonadPlus m) => m a -> m s -> m [a] -sepBy1' p s = scan - where scan = liftM2' (:) p ((s >> scan) `mplus` return []) -{-# SPECIALIZE sepBy1' :: Parser ByteString a -> Parser ByteString s - -> Parser ByteString [a] #-} - --- | @manyTill p end@ applies action @p@ /zero/ or more times until --- action @end@ succeeds, and returns the list of values returned by --- @p@. This can be used to scan comments: --- --- > simpleComment = string "<!--" *> manyTill anyChar (string "-->") --- --- (Note the overlapping parsers @anyChar@ and @string \"-->\"@. --- While this will work, it is not very efficient, as it will cause a --- lot of backtracking.) -manyTill :: Alternative f => f a -> f b -> f [a] -manyTill p end = scan - where scan = (end *> pure []) <|> liftA2 (:) p scan -{-# SPECIALIZE manyTill :: Parser ByteString a -> Parser ByteString b - -> Parser ByteString [a] #-} - --- | @manyTill' p end@ applies action @p@ /zero/ or more times until --- action @end@ succeeds, and returns the list of values returned by --- @p@. This can be used to scan comments: --- --- > simpleComment = string "<!--" *> manyTill' anyChar (string "-->") --- --- (Note the overlapping parsers @anyChar@ and @string \"-->\"@. --- While this will work, it is not very efficient, as it will cause a --- lot of backtracking.) --- --- The value returned by @p@ is forced to WHNF. -manyTill' :: (MonadPlus m) => m a -> m b -> m [a] -manyTill' p end = scan - where scan = (end >> return []) `mplus` liftM2' (:) p scan -{-# SPECIALIZE manyTill' :: Parser ByteString a -> Parser ByteString b - -> Parser ByteString [a] #-} - --- | Skip zero or more instances of an action. -skipMany :: Alternative f => f a -> f () -skipMany p = scan - where scan = (p *> scan) <|> pure () -{-# SPECIALIZE skipMany :: Parser ByteString a -> Parser ByteString () #-} - --- | Skip one or more instances of an action. -skipMany1 :: Alternative f => f a -> f () -skipMany1 p = p *> skipMany p -{-# SPECIALIZE skipMany1 :: Parser ByteString a -> Parser ByteString () #-} - --- | Apply the given action repeatedly, returning every result. -count :: Monad m => Int -> m a -> m [a] -count n p = sequence (replicate n p) -{-# INLINE count #-} - --- | Combine two alternatives. -eitherP :: (Alternative f) => f a -> f b -> f (Either a b) -eitherP a b = (Left <$> a) <|> (Right <$> b) -{-# INLINE eitherP #-} - --- | If a parser has returned a 'T.Partial' result, supply it with more --- input. -feed :: Monoid i => IResult i r -> i -> IResult i r -feed (Fail t ctxs msg) d = Fail (mappend t d) ctxs msg -feed (Partial k) d = k d -feed (Done t r) d = Done (mappend t d) r -{-# INLINE feed #-} - --- | Apply a parser without consuming any input. -lookAhead :: Parser i a -> Parser i a -lookAhead p = Parser $ \t pos more lose succ -> - let succ' t' _pos' more' = succ t' pos more' - in runParser p t pos more lose succ' -{-# INLINE lookAhead #-} diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Internal.hs b/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Internal.hs deleted file mode 100644 index ee758b26..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Internal.hs +++ /dev/null @@ -1,157 +0,0 @@ -{-# LANGUAGE BangPatterns, CPP, ScopedTypeVariables #-} --- | --- Module : Data.Attoparsec.Internal --- Copyright : Bryan O'Sullivan 2007-2015 --- License : BSD3 --- --- Maintainer : bos@serpentine.com --- Stability : experimental --- Portability : unknown --- --- Simple, efficient parser combinators, loosely based on the Parsec --- library. - -module Data.Attoparsec.Internal - ( compareResults - , prompt - , demandInput - , demandInput_ - , wantInput - , endOfInput - , atEnd - , satisfyElem - , concatReverse - ) where - -#if !MIN_VERSION_base(4,8,0) -import Control.Applicative ((<$>)) -import Data.Monoid (Monoid, mconcat) -#endif -import Data.Attoparsec.Internal.Types -import Data.ByteString (ByteString) -import Prelude hiding (succ) - --- | Compare two 'IResult' values for equality. --- --- If both 'IResult's are 'Partial', the result will be 'Nothing', as --- they are incomplete and hence their equality cannot be known. --- (This is why there is no 'Eq' instance for 'IResult'.) -compareResults :: (Eq i, Eq r) => IResult i r -> IResult i r -> Maybe Bool -compareResults (Fail t0 ctxs0 msg0) (Fail t1 ctxs1 msg1) = - Just (t0 == t1 && ctxs0 == ctxs1 && msg0 == msg1) -compareResults (Done t0 r0) (Done t1 r1) = - Just (t0 == t1 && r0 == r1) -compareResults (Partial _) (Partial _) = Nothing -compareResults _ _ = Just False - --- | Ask for input. If we receive any, pass the augmented input to a --- success continuation, otherwise to a failure continuation. -prompt :: Chunk t - => State t -> Pos -> More - -> (State t -> Pos -> More -> IResult t r) - -> (State t -> Pos -> More -> IResult t r) - -> IResult t r -prompt t pos _more lose succ = Partial $ \s -> - if nullChunk s - then lose t pos Complete - else succ (pappendChunk t s) pos Incomplete -{-# SPECIALIZE prompt :: State ByteString -> Pos -> More - -> (State ByteString -> Pos -> More - -> IResult ByteString r) - -> (State ByteString -> Pos -> More - -> IResult ByteString r) - -> IResult ByteString r #-} - --- | Immediately demand more input via a 'Partial' continuation --- result. -demandInput :: Chunk t => Parser t () -demandInput = Parser $ \t pos more lose succ -> - case more of - Complete -> lose t pos more [] "not enough input" - _ -> let lose' _ pos' more' = lose t pos' more' [] "not enough input" - succ' t' pos' more' = succ t' pos' more' () - in prompt t pos more lose' succ' -{-# SPECIALIZE demandInput :: Parser ByteString () #-} - --- | Immediately demand more input via a 'Partial' continuation --- result. Return the new input. -demandInput_ :: Chunk t => Parser t t -demandInput_ = Parser $ \t pos more lose succ -> - case more of - Complete -> lose t pos more [] "not enough input" - _ -> Partial $ \s -> - if nullChunk s - then lose t pos Complete [] "not enough input" - else succ (pappendChunk t s) pos more s -{-# SPECIALIZE demandInput_ :: Parser ByteString ByteString #-} - --- | This parser always succeeds. It returns 'True' if any input is --- available either immediately or on demand, and 'False' if the end --- of all input has been reached. -wantInput :: forall t . Chunk t => Parser t Bool -wantInput = Parser $ \t pos more _lose succ -> - case () of - _ | pos < atBufferEnd (undefined :: t) t -> succ t pos more True - | more == Complete -> succ t pos more False - | otherwise -> let lose' t' pos' more' = succ t' pos' more' False - succ' t' pos' more' = succ t' pos' more' True - in prompt t pos more lose' succ' -{-# INLINE wantInput #-} - --- | Match only if all input has been consumed. -endOfInput :: forall t . Chunk t => Parser t () -endOfInput = Parser $ \t pos more lose succ -> - case () of - _| pos < atBufferEnd (undefined :: t) t -> lose t pos more [] "endOfInput" - | more == Complete -> succ t pos more () - | otherwise -> - let lose' t' pos' more' _ctx _msg = succ t' pos' more' () - succ' t' pos' more' _a = lose t' pos' more' [] "endOfInput" - in runParser demandInput t pos more lose' succ' -{-# SPECIALIZE endOfInput :: Parser ByteString () #-} - --- | Return an indication of whether the end of input has been --- reached. -atEnd :: Chunk t => Parser t Bool -atEnd = not <$> wantInput -{-# INLINE atEnd #-} - -satisfySuspended :: forall t r . Chunk t - => (ChunkElem t -> Bool) - -> State t -> Pos -> More - -> Failure t (State t) r - -> Success t (State t) (ChunkElem t) r - -> IResult t r -satisfySuspended p t pos more lose succ = - runParser (demandInput >> go) t pos more lose succ - where go = Parser $ \t' pos' more' lose' succ' -> - case bufferElemAt (undefined :: t) pos' t' of - Just (e, l) | p e -> succ' t' (pos' + Pos l) more' e - | otherwise -> lose' t' pos' more' [] "satisfyElem" - Nothing -> runParser (demandInput >> go) t' pos' more' lose' succ' -{-# SPECIALIZE satisfySuspended :: (ChunkElem ByteString -> Bool) - -> State ByteString -> Pos -> More - -> Failure ByteString (State ByteString) r - -> Success ByteString (State ByteString) - (ChunkElem ByteString) r - -> IResult ByteString r #-} - --- | The parser @satisfyElem p@ succeeds for any chunk element for which the --- predicate @p@ returns 'True'. Returns the element that is --- actually parsed. -satisfyElem :: forall t . Chunk t - => (ChunkElem t -> Bool) -> Parser t (ChunkElem t) -satisfyElem p = Parser $ \t pos more lose succ -> - case bufferElemAt (undefined :: t) pos t of - Just (e, l) | p e -> succ t (pos + Pos l) more e - | otherwise -> lose t pos more [] "satisfyElem" - Nothing -> satisfySuspended p t pos more lose succ -{-# INLINE satisfyElem #-} - --- | Concatenate a monoid after reversing its elements. Used to --- glue together a series of textual chunks that have been accumulated --- \"backwards\". -concatReverse :: Monoid m => [m] -> m -concatReverse [x] = x -concatReverse xs = mconcat (reverse xs) -{-# INLINE concatReverse #-} diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Internal/Fhthagn.hs b/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Internal/Fhthagn.hs deleted file mode 100644 index 0e00ed2c..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Internal/Fhthagn.hs +++ /dev/null @@ -1,18 +0,0 @@ -{-# LANGUAGE BangPatterns, Rank2Types, OverloadedStrings, - RecordWildCards, MagicHash, UnboxedTuples #-} - -module Data.Attoparsec.Internal.Fhthagn - ( - inlinePerformIO - ) where - -import GHC.Base (realWorld#) -import GHC.IO (IO(IO)) - --- | Just like unsafePerformIO, but we inline it. Big performance gains as --- it exposes lots of things to further inlining. /Very unsafe/. In --- particular, you should do no memory allocation inside an --- 'inlinePerformIO' block. On Hugs this is just @unsafePerformIO@. -inlinePerformIO :: IO a -> a -inlinePerformIO (IO m) = case m realWorld# of (# _, r #) -> r -{-# INLINE inlinePerformIO #-} diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Internal/Types.hs b/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Internal/Types.hs deleted file mode 100644 index 96bc319e..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Internal/Types.hs +++ /dev/null @@ -1,243 +0,0 @@ -{-# LANGUAGE BangPatterns, GeneralizedNewtypeDeriving, OverloadedStrings, - Rank2Types, RecordWildCards, TypeFamilies #-} --- | --- Module : Data.Attoparsec.Internal.Types --- Copyright : Bryan O'Sullivan 2007-2015 --- License : BSD3 --- --- Maintainer : bos@serpentine.com --- Stability : experimental --- Portability : unknown --- --- Simple, efficient parser combinators, loosely based on the Parsec --- library. - -module Data.Attoparsec.Internal.Types - ( - Parser(..) - , State - , Failure - , Success - , Pos(..) - , IResult(..) - , More(..) - , (<>) - , Chunk(..) - ) where - -import Control.Applicative as App (Applicative(..), (<$>)) -import Control.Applicative (Alternative(..)) -import Control.DeepSeq (NFData(rnf)) -import Control.Monad (MonadPlus(..)) -import qualified Control.Monad.Fail as Fail (MonadFail(..)) -import Data.Monoid as Mon (Monoid(..)) -import Data.Semigroup (Semigroup(..)) -import Data.Word (Word8) -import Data.ByteString (ByteString) -import qualified Data.ByteString as BS -import Data.ByteString.Internal (w2c) -import Prelude hiding (getChar, succ) -import qualified Data.Attoparsec.ByteString.Buffer as B - -newtype Pos = Pos { fromPos :: Int } - deriving (Eq, Ord, Show, Num) - --- | The result of a parse. This is parameterised over the type @i@ --- of string that was processed. --- --- This type is an instance of 'Functor', where 'fmap' transforms the --- value in a 'Done' result. -data IResult i r = - Fail i [String] String - -- ^ The parse failed. The @i@ parameter is the input that had - -- not yet been consumed when the failure occurred. The - -- @[@'String'@]@ is a list of contexts in which the error - -- occurred. The 'String' is the message describing the error, if - -- any. - | Partial (i -> IResult i r) - -- ^ Supply this continuation with more input so that the parser - -- can resume. To indicate that no more input is available, pass - -- an empty string to the continuation. - -- - -- __Note__: if you get a 'Partial' result, do not call its - -- continuation more than once. - | Done i r - -- ^ The parse succeeded. The @i@ parameter is the input that had - -- not yet been consumed (if any) when the parse succeeded. - -instance (Show i, Show r) => Show (IResult i r) where - showsPrec d ir = showParen (d > 10) $ - case ir of - (Fail t stk msg) -> showString "Fail" . f t . f stk . f msg - (Partial _) -> showString "Partial _" - (Done t r) -> showString "Done" . f t . f r - where f :: Show a => a -> ShowS - f x = showChar ' ' . showsPrec 11 x - -instance (NFData i, NFData r) => NFData (IResult i r) where - rnf (Fail t stk msg) = rnf t `seq` rnf stk `seq` rnf msg - rnf (Partial _) = () - rnf (Done t r) = rnf t `seq` rnf r - {-# INLINE rnf #-} - -instance Functor (IResult i) where - fmap _ (Fail t stk msg) = Fail t stk msg - fmap f (Partial k) = Partial (fmap f . k) - fmap f (Done t r) = Done t (f r) - --- | The core parser type. This is parameterised over the type @i@ --- of string being processed. --- --- This type is an instance of the following classes: --- --- * 'Monad', where 'fail' throws an exception (i.e. fails) with an --- error message. --- --- * 'Functor' and 'Applicative', which follow the usual definitions. --- --- * 'MonadPlus', where 'mzero' fails (with no error message) and --- 'mplus' executes the right-hand parser if the left-hand one --- fails. When the parser on the right executes, the input is reset --- to the same state as the parser on the left started with. (In --- other words, attoparsec is a backtracking parser that supports --- arbitrary lookahead.) --- --- * 'Alternative', which follows 'MonadPlus'. -newtype Parser i a = Parser { - runParser :: forall r. - State i -> Pos -> More - -> Failure i (State i) r - -> Success i (State i) a r - -> IResult i r - } - -type family State i -type instance State ByteString = B.Buffer - -type Failure i t r = t -> Pos -> More -> [String] -> String - -> IResult i r -type Success i t a r = t -> Pos -> More -> a -> IResult i r - --- | Have we read all available input? -data More = Complete | Incomplete - deriving (Eq, Show) - -instance Semigroup More where - c@Complete <> _ = c - _ <> m = m - -instance Mon.Monoid More where - mappend = (<>) - mempty = Incomplete - -instance Monad (Parser i) where - fail = Fail.fail - {-# INLINE fail #-} - - return = App.pure - {-# INLINE return #-} - - m >>= k = Parser $ \t !pos more lose succ -> - let succ' t' !pos' more' a = runParser (k a) t' pos' more' lose succ - in runParser m t pos more lose succ' - {-# INLINE (>>=) #-} - - (>>) = (*>) - {-# INLINE (>>) #-} - - -instance Fail.MonadFail (Parser i) where - fail err = Parser $ \t pos more lose _succ -> lose t pos more [] msg - where msg = "Failed reading: " ++ err - {-# INLINE fail #-} - -plus :: Parser i a -> Parser i a -> Parser i a -plus f g = Parser $ \t pos more lose succ -> - let lose' t' _pos' more' _ctx _msg = runParser g t' pos more' lose succ - in runParser f t pos more lose' succ - -instance MonadPlus (Parser i) where - mzero = fail "mzero" - {-# INLINE mzero #-} - mplus = plus - -instance Functor (Parser i) where - fmap f p = Parser $ \t pos more lose succ -> - let succ' t' pos' more' a = succ t' pos' more' (f a) - in runParser p t pos more lose succ' - {-# INLINE fmap #-} - -apP :: Parser i (a -> b) -> Parser i a -> Parser i b -apP d e = do - b <- d - a <- e - return (b a) -{-# INLINE apP #-} - -instance Applicative (Parser i) where - pure v = Parser $ \t pos more _lose succ -> succ t pos more v - {-# INLINE pure #-} - (<*>) = apP - {-# INLINE (<*>) #-} - m *> k = m >>= \_ -> k - {-# INLINE (*>) #-} - x <* y = x >>= \a -> y >> pure a - {-# INLINE (<*) #-} - -instance Semigroup (Parser i a) where - (<>) = plus - {-# INLINE (<>) #-} - -instance Monoid (Parser i a) where - mempty = fail "mempty" - {-# INLINE mempty #-} - mappend = (<>) - {-# INLINE mappend #-} - -instance Alternative (Parser i) where - empty = fail "empty" - {-# INLINE empty #-} - - (<|>) = plus - {-# INLINE (<|>) #-} - - many v = many_v - where many_v = some_v <|> pure [] - some_v = (:) App.<$> v <*> many_v - {-# INLINE many #-} - - some v = some_v - where - many_v = some_v <|> pure [] - some_v = (:) <$> v <*> many_v - {-# INLINE some #-} - --- | A common interface for input chunks. -class Monoid c => Chunk c where - type ChunkElem c - -- | Test if the chunk is empty. - nullChunk :: c -> Bool - -- | Append chunk to a buffer. - pappendChunk :: State c -> c -> State c - -- | Position at the end of a buffer. The first argument is ignored. - atBufferEnd :: c -> State c -> Pos - -- | Return the buffer element at the given position along with its length. - bufferElemAt :: c -> Pos -> State c -> Maybe (ChunkElem c, Int) - -- | Map an element to the corresponding character. - -- The first argument is ignored. - chunkElemToChar :: c -> ChunkElem c -> Char - -instance Chunk ByteString where - type ChunkElem ByteString = Word8 - nullChunk = BS.null - {-# INLINE nullChunk #-} - pappendChunk = B.pappend - {-# INLINE pappendChunk #-} - atBufferEnd _ = Pos . B.length - {-# INLINE atBufferEnd #-} - bufferElemAt _ (Pos i) buf - | i < B.length buf = Just (B.unsafeIndex buf i, 1) - | otherwise = Nothing - {-# INLINE bufferElemAt #-} - chunkElemToChar _ = w2c - {-# INLINE chunkElemToChar #-} diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Number.hs b/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Number.hs deleted file mode 100644 index d0970d90..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/Data/Attoparsec/Number.hs +++ /dev/null @@ -1,137 +0,0 @@ -{-# LANGUAGE DeriveDataTypeable #-} --- | --- Module : Data.Attoparsec.Number --- Copyright : Bryan O'Sullivan 2007-2015 --- License : BSD3 --- --- Maintainer : bos@serpentine.com --- Stability : experimental --- Portability : unknown --- --- This module is deprecated, and both the module and 'Number' type --- will be removed in the next major release. Use the --- <http://hackage.haskell.org/package/scientific scientific> package --- and the 'Data.Scientific.Scientific' type instead. --- --- A simple number type, useful for parsing both exact and inexact --- quantities without losing much precision. -module Data.Attoparsec.Number - {-# DEPRECATED "This module will be removed in the next major release." #-} - ( - Number(..) - ) where - -import Control.DeepSeq (NFData(rnf)) -import Data.Data (Data) -import Data.Function (on) -import Data.Typeable (Typeable) - --- | A numeric type that can represent integers accurately, and --- floating point numbers to the precision of a 'Double'. --- --- /Note/: this type is deprecated, and will be removed in the next --- major release. Use the 'Data.Scientific.Scientific' type instead. -data Number = I !Integer - | D {-# UNPACK #-} !Double - deriving (Typeable, Data) -{-# DEPRECATED Number "Use Scientific instead." #-} - -instance Show Number where - show (I a) = show a - show (D a) = show a - -instance NFData Number where - rnf (I _) = () - rnf (D _) = () - {-# INLINE rnf #-} - -binop :: (Integer -> Integer -> a) -> (Double -> Double -> a) - -> Number -> Number -> a -binop _ d (D a) (D b) = d a b -binop i _ (I a) (I b) = i a b -binop _ d (D a) (I b) = d a (fromIntegral b) -binop _ d (I a) (D b) = d (fromIntegral a) b -{-# INLINE binop #-} - -instance Eq Number where - (==) = binop (==) (==) - {-# INLINE (==) #-} - - (/=) = binop (/=) (/=) - {-# INLINE (/=) #-} - -instance Ord Number where - (<) = binop (<) (<) - {-# INLINE (<) #-} - - (<=) = binop (<=) (<=) - {-# INLINE (<=) #-} - - (>) = binop (>) (>) - {-# INLINE (>) #-} - - (>=) = binop (>=) (>=) - {-# INLINE (>=) #-} - - compare = binop compare compare - {-# INLINE compare #-} - -instance Num Number where - (+) = binop (((I$!).) . (+)) (((D$!).) . (+)) - {-# INLINE (+) #-} - - (-) = binop (((I$!).) . (-)) (((D$!).) . (-)) - {-# INLINE (-) #-} - - (*) = binop (((I$!).) . (*)) (((D$!).) . (*)) - {-# INLINE (*) #-} - - abs (I a) = I $! abs a - abs (D a) = D $! abs a - {-# INLINE abs #-} - - negate (I a) = I $! negate a - negate (D a) = D $! negate a - {-# INLINE negate #-} - - signum (I a) = I $! signum a - signum (D a) = D $! signum a - {-# INLINE signum #-} - - fromInteger = (I$!) . fromInteger - {-# INLINE fromInteger #-} - -instance Real Number where - toRational (I a) = fromIntegral a - toRational (D a) = toRational a - {-# INLINE toRational #-} - -instance Fractional Number where - fromRational = (D$!) . fromRational - {-# INLINE fromRational #-} - - (/) = binop (((D$!).) . (/) `on` fromIntegral) - (((D$!).) . (/)) - {-# INLINE (/) #-} - - recip (I a) = D $! recip (fromIntegral a) - recip (D a) = D $! recip a - {-# INLINE recip #-} - -instance RealFrac Number where - properFraction (I a) = (fromIntegral a,0) - properFraction (D a) = case properFraction a of - (i,d) -> (i,D d) - {-# INLINE properFraction #-} - truncate (I a) = fromIntegral a - truncate (D a) = truncate a - {-# INLINE truncate #-} - round (I a) = fromIntegral a - round (D a) = round a - {-# INLINE round #-} - ceiling (I a) = fromIntegral a - ceiling (D a) = ceiling a - {-# INLINE ceiling #-} - floor (I a) = fromIntegral a - floor (D a) = floor a - {-# INLINE floor #-} diff --git a/haddock-library/vendor/attoparsec-0.13.1.0/LICENSE b/haddock-library/vendor/attoparsec-0.13.1.0/LICENSE deleted file mode 100644 index 97392a62..00000000 --- a/haddock-library/vendor/attoparsec-0.13.1.0/LICENSE +++ /dev/null @@ -1,30 +0,0 @@ -Copyright (c) Lennart Kolmodin - -All rights reserved. - -Redistribution and use in source and binary forms, with or without -modification, are permitted provided that the following conditions -are met: - -1. Redistributions of source code must retain the above copyright - notice, this list of conditions and the following disclaimer. - -2. Redistributions in binary form must reproduce the above copyright - notice, this list of conditions and the following disclaimer in the - documentation and/or other materials provided with the distribution. - -3. Neither the name of the author nor the names of his contributors - may be used to endorse or promote products derived from this software - without specific prior written permission. - -THIS SOFTWARE IS PROVIDED BY THE CONTRIBUTORS ``AS IS'' AND ANY EXPRESS -OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED -WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE -DISCLAIMED. IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE LIABLE FOR -ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, -STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN -ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE -POSSIBILITY OF SUCH DAMAGE. diff --git a/haddock-test/src/Test/Haddock/Config.hs b/haddock-test/src/Test/Haddock/Config.hs index 988636e4..8b395b6c 100644 --- a/haddock-test/src/Test/Haddock/Config.hs +++ b/haddock-test/src/Test/Haddock/Config.hs @@ -98,6 +98,7 @@ data Flag = FlagHaddockPath FilePath | FlagHaddockOptions String | FlagHaddockStdOut FilePath + | FlagGhcPath FilePath | FlagDiffTool FilePath | FlagNoDiff | FlagAccept @@ -108,6 +109,8 @@ data Flag flagsHaddockPath :: [Flag] -> Maybe FilePath flagsHaddockPath flags = mlast [ path | FlagHaddockPath path <- flags ] +flagsGhcPath :: [Flag] -> Maybe FilePath +flagsGhcPath flags = mlast [ path | FlagGhcPath path <- flags ] flagsHaddockOptions :: [Flag] -> [String] flagsHaddockOptions flags = concat @@ -130,6 +133,8 @@ options = "additional options to run Haddock with" , Option [] ["haddock-stdout"] (ReqArg FlagHaddockStdOut "FILE") "where to redirect Haddock output" + , Option [] ["ghc-path"] (ReqArg FlagGhcPath "FILE") + "path ghc executable" , Option [] ["diff-tool"] (ReqArg FlagDiffTool "PATH") "diff tool to use when printing failed cases" , Option ['a'] ["accept"] (NoArg FlagAccept) @@ -178,8 +183,11 @@ loadConfig ccfg dcfg flags files = do hPutStrLn stderr "Haddock executable not found" exitFailure - ghcPath <- init <$> rawSystemStdout normal cfgHaddockPath - ["--print-ghc-path"] + ghcPath <- case flagsGhcPath flags of + Just fp -> return fp + Nothing -> init <$> rawSystemStdout normal + cfgHaddockPath + ["--print-ghc-path"] printVersions cfgEnv cfgHaddockPath @@ -189,6 +197,7 @@ loadConfig ccfg dcfg flags files = do [ pure ["--no-warnings"] , pure ["--odir=" ++ dcfgOutDir dcfg] , pure ["--optghc=-w"] + , pure ["--optghc=-hide-all-packages"] , pure $ flagsHaddockOptions flags , baseDependencies ghcPath ] @@ -236,13 +245,21 @@ baseDependencies ghcPath = do #else pkgIndex <- getInstalledPackages normal [GlobalPackageDB] cfg #endif - mapM (getDependency pkgIndex) ["base", "process", "ghc-prim"] + let + pkgs = + [ "array" + , "base" + , "ghc-prim" + , "process" + , "template-haskell" + ] + concat `fmap` mapM (getDependency pkgIndex) pkgs where getDependency pkgIndex name = case ifaces pkgIndex name of [] -> do hPutStrLn stderr $ "Couldn't find base test dependency: " ++ name exitFailure - (ifArg:_) -> pure ifArg + (ifArg:_) -> pure ["--optghc=-package" ++ name, ifArg] ifaces pkgIndex name = do pkg <- join $ snd <$> lookupPackageName pkgIndex (mkPackageName name) iface <$> haddockInterfaces pkg <*> haddockHTMLs pkg diff --git a/haddock.cabal b/haddock.cabal index e9280eb2..af606894 100644 --- a/haddock.cabal +++ b/haddock.cabal @@ -1,5 +1,6 @@ +cabal-version: 2.0 name: haddock -version: 2.18.2 +version: 2.20.0 synopsis: A documentation-generation tool for Haskell libraries description: This is Haddock, a tool for automatically generating documentation @@ -32,8 +33,7 @@ bug-reports: https://github.com/haskell/haddock/issues copyright: (c) Simon Marlow, David Waern category: Documentation build-type: Simple -cabal-version: >= 2.0 -tested-with: GHC==8.2.* +tested-with: GHC==8.4.* extra-source-files: CHANGES.md @@ -62,11 +62,12 @@ executable haddock hs-source-dirs: driver ghc-options: -funbox-strict-fields -Wall -fwarn-tabs -O2 -threaded - -- haddock typically only supports a single GHC major version + -- haddock typically only supports a single GHC major version build-depends: - base >= 4.3 && < 4.13 + base ^>= 4.12.0 + if flag(in-ghc-tree) - hs-source-dirs: haddock-api/src, haddock-library/vendor/attoparsec-0.13.1.0, haddock-library/src + hs-source-dirs: haddock-api/src, haddock-library/src cpp-options: -DIN_GHC_TREE build-depends: filepath, @@ -79,6 +80,8 @@ executable haddock ghc-boot, ghc == 8.5.*, bytestring, + parsec, + text, transformers other-modules: @@ -86,17 +89,6 @@ executable haddock Documentation.Haddock.Parser.Monad Documentation.Haddock.Types Documentation.Haddock.Doc - Data.Attoparsec - Data.Attoparsec.ByteString - Data.Attoparsec.ByteString.Buffer - Data.Attoparsec.ByteString.Char8 - Data.Attoparsec.ByteString.FastSet - Data.Attoparsec.ByteString.Internal - Data.Attoparsec.Combinator - Data.Attoparsec.Internal - Data.Attoparsec.Internal.Fhthagn - Data.Attoparsec.Internal.Types - Data.Attoparsec.Number Documentation.Haddock.Utf8 Documentation.Haddock.Parser.Util Documentation.Haddock.Markup @@ -150,7 +142,7 @@ executable haddock else -- in order for haddock's advertised version number to have proper meaning, -- we pin down to a single haddock-api version. - build-depends: haddock-api == 2.18.2 + build-depends: haddock-api == 2.20.0 test-suite html-test type: exitcode-stdio-1.0 diff --git a/hoogle-test/ref/Bug806/test.txt b/hoogle-test/ref/Bug806/test.txt new file mode 100644 index 00000000..d9a908b3 --- /dev/null +++ b/hoogle-test/ref/Bug806/test.txt @@ -0,0 +1,24 @@ +-- Hoogle documentation, generated by Haddock +-- See Hoogle, http://www.haskell.org/hoogle/ + +@package test +@version 0.0.0 + +module Bug806 + +-- | <a>F1</a> docs +type family F1 a b :: * -> * + +-- | <a>F2</a> docs +type family F2 a b :: * -> * + +-- | <a>D</a> docs +data family D a :: * -> * +v :: Int + +-- | <a>C</a> docs +class C a where { + + -- | <a>AT</a> docs + type family AT a; +} diff --git a/hoogle-test/ref/Bug825/test.txt b/hoogle-test/ref/Bug825/test.txt new file mode 100644 index 00000000..a88202dc --- /dev/null +++ b/hoogle-test/ref/Bug825/test.txt @@ -0,0 +1,9 @@ +-- Hoogle documentation, generated by Haddock +-- See Hoogle, http://www.haskell.org/hoogle/ + +@package test +@version 0.0.0 + +module Bug825 +data a :~: b +data (:~~:) a b diff --git a/hoogle-test/ref/type-sigs/test.txt b/hoogle-test/ref/type-sigs/test.txt new file mode 100644 index 00000000..ec5f5043 --- /dev/null +++ b/hoogle-test/ref/type-sigs/test.txt @@ -0,0 +1,16 @@ +-- Hoogle documentation, generated by Haddock +-- See Hoogle, http://www.haskell.org/hoogle/ + +@package test +@version 0.0.0 + +module ReaderT +newtype ReaderT r m a +ReaderT :: r -> m a -> ReaderT r m a +[runReaderT] :: ReaderT r m a -> r -> m a + +module ReaderTReexport +newtype ReaderT r m a +ReaderT :: r -> m a -> ReaderT r m a +[runReaderT] :: ReaderT r m a -> r -> m a +runReaderT :: ReaderT r m a -> r -> m a diff --git a/hoogle-test/src/Bug806/Bug806.hs b/hoogle-test/src/Bug806/Bug806.hs new file mode 100644 index 00000000..6efcb5cf --- /dev/null +++ b/hoogle-test/src/Bug806/Bug806.hs @@ -0,0 +1,23 @@ +{-# LANGUAGE KindSignatures #-} +{-# LANGUAGE TypeFamilies #-} +{-# LANGUAGE UndecidableInstances #-} +module Bug806 where + +import Data.Proxy + +-- | 'F1' docs +type family F1 a b :: * -> * +-- | 'F2' docs +type family F2 a b :: * -> * where + F2 Int b = Maybe + F2 a b = [] +-- | 'D' docs +data family D a :: * -> * + +v :: Int +v = 42 + +-- | 'C' docs +class C a where + -- | 'AT' docs + type AT a diff --git a/hoogle-test/src/Bug825/Bug825.hs b/hoogle-test/src/Bug825/Bug825.hs new file mode 100644 index 00000000..bfe07139 --- /dev/null +++ b/hoogle-test/src/Bug825/Bug825.hs @@ -0,0 +1,6 @@ +{-# LANGUAGE MultiParamTypeClasses #-} +{-# LANGUAGE TypeOperators #-} +module Bug825 where + +data a :~: b +data (:~~:) a b diff --git a/hoogle-test/src/type-sigs/ReaderT.hs b/hoogle-test/src/type-sigs/ReaderT.hs new file mode 100644 index 00000000..009c7ed2 --- /dev/null +++ b/hoogle-test/src/type-sigs/ReaderT.hs @@ -0,0 +1,3 @@ +module ReaderT where + +newtype ReaderT r m a = ReaderT { runReaderT :: r -> m a } diff --git a/hoogle-test/src/type-sigs/ReaderTReexport.hs b/hoogle-test/src/type-sigs/ReaderTReexport.hs new file mode 100644 index 00000000..21fa44ee --- /dev/null +++ b/hoogle-test/src/type-sigs/ReaderTReexport.hs @@ -0,0 +1,3 @@ +module ReaderTReexport (ReaderT(..), runReaderT) where + +import ReaderT diff --git a/html-test/Main.hs b/html-test/Main.hs index 67dbeec6..d65a5087 100755 --- a/html-test/Main.hs +++ b/html-test/Main.hs @@ -47,7 +47,22 @@ stripIfRequired mdl = preserveLinksModules :: [String] preserveLinksModules = ["Bug253"] +ingoredTests :: [FilePath] +ingoredTests = + [ + -- Currently some declarations are exported twice + -- we need a reliable way to deduplicate here. + -- Happens since PR #688. + "B" + + -- ignore-exports flag broke with PR #688. We use + -- the Avails calculated by GHC now. Probably + -- requires a change to GHC to "ignore" a modules + -- export list reliably. + , "IgnoreExports" + ] checkIgnore :: FilePath -> Bool +checkIgnore file | takeBaseName file `elem` ingoredTests = True checkIgnore file@(c:_) | takeExtension file == ".html" && isUpper c = False checkIgnore _ = True diff --git a/html-test/ref/A.html b/html-test/ref/A.html index 1fbfb371..c6965abc 100644 --- a/html-test/ref/A.html +++ b/html-test/ref/A.html @@ -54,15 +54,11 @@ ><li class="src short" ><a href="#" >other</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >test2</a - > :: <a href="#" - >Bool</a - ></li + > :: Bool</li ><li class="src short" ><span class="keyword" >data</span @@ -74,9 +70,7 @@ ><li class="src short" ><a href="#" >reExport</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div @@ -111,9 +105,7 @@ ><p class="src" ><a id="v:other" class="def" >other</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ></div @@ -121,9 +113,7 @@ ><p class="src" ><a id="v:test2" class="def" >test2</a - > :: <a href="#" - >Bool</a - > <a href="#" class="selflink" + > :: Bool <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -165,9 +155,7 @@ ><p class="src" ><a id="v:reExport" class="def" >reExport</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/Bug1.html b/html-test/ref/Bug1.html index e6ee486b..d5f9052e 100644 --- a/html-test/ref/Bug1.html +++ b/html-test/ref/Bug1.html @@ -70,7 +70,7 @@ ><p >We should have different anchors for constructors and types/classes. This hyperlink should point to the type constructor by default: <code - ><a href="#" + ><a href="#" title="Bug1" >T</a ></code >.</p diff --git a/html-test/ref/Bug2.html b/html-test/ref/Bug2.html index b10195c4..d2d0efd9 100644 --- a/html-test/ref/Bug2.html +++ b/html-test/ref/Bug2.html @@ -45,7 +45,7 @@ ><p class="src" ><a id="v:x" class="def" >x</a - > :: <a href="#" + > :: <a href="#" title="A" >A</a > <a href="#" class="selflink" >#</a diff --git a/html-test/ref/Bug253.html b/html-test/ref/Bug253.html index 178d70fe..57b1b164 100644 --- a/html-test/ref/Bug253.html +++ b/html-test/ref/Bug253.html @@ -81,7 +81,7 @@ >This link should generate <code >#v</code > anchor: <code - ><a href="#" + ><a href="#" title="DoesNotExist" >fakeFakeFake</a ></code ></p diff --git a/html-test/ref/Bug26.html b/html-test/ref/Bug26.html index 376c2ce6..a363fef3 100644 --- a/html-test/ref/Bug26.html +++ b/html-test/ref/Bug26.html @@ -71,7 +71,11 @@ > a <span class="keyword" >where</span ><ul class="subs" - ></ul + ><li + ><a href="#" + >c_f</a + > :: a</li + ></ul ></li ></ul ></details @@ -126,14 +130,6 @@ >Since: 1.0</em ></p ></div - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >c_f</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p @@ -160,7 +156,7 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:C:C:1" ></span - > <a href="#" + > <a href="#" title="Bug26" >C</a > ()</span > <a href="#" class="selflink" @@ -180,7 +176,11 @@ ><details id="i:ic:C:C:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Bug26</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" diff --git a/html-test/ref/Bug280.html b/html-test/ref/Bug280.html index da1e6b13..f2d25057 100644 --- a/html-test/ref/Bug280.html +++ b/html-test/ref/Bug280.html @@ -61,9 +61,7 @@ ><p class="src" ><a id="v:x" class="def" >x</a - > :: [<a href="#" - >Char</a - >] <a href="#" class="selflink" + > :: [Char] <a href="#" class="selflink" >#</a ></p ></div diff --git a/html-test/ref/Bug294.html b/html-test/ref/Bug294.html index 87a03731..790c1894 100644 --- a/html-test/ref/Bug294.html +++ b/html-test/ref/Bug294.html @@ -62,9 +62,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="Bug294" >DP</a - > <a href="#" + > <a href="#" title="Bug294" >A</a ></span > <a href="#" class="selflink" @@ -78,16 +78,20 @@ ><details id="i:id:A:DP:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >Bug294</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="Bug294" >DP</a - > <a href="#" + > <a href="#" title="Bug294" >A</a > = <a id="v:ProblemCtor-39-" class="def" >ProblemCtor'</a - > <a href="#" + > <a href="#" title="Bug294" >A</a ></div ></details @@ -100,7 +104,9 @@ ></span > <span class="keyword" >data</span - > TP <a href="#" + > <a href="#" title="Bug294" + >TP</a + > <a href="#" title="Bug294" >A</a ></span > <a href="#" class="selflink" @@ -114,14 +120,20 @@ ><details id="i:id:A:TP:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >Bug294</a + ></p + > <div class="src" ><span class="keyword" >data</span - > TP <a href="#" + > <a href="#" title="Bug294" + >TP</a + > <a href="#" title="Bug294" >A</a > = <a id="v:ProblemCtor" class="def" >ProblemCtor</a - > <a href="#" + > <a href="#" title="Bug294" >A</a ></div ></details @@ -135,9 +147,9 @@ ><p class="src" ><a id="v:problemField" class="def" >problemField</a - > :: TO <a href="#" + > :: TO <a href="#" title="Bug294" >A</a - > -> <a href="#" + > -> <a href="#" title="Bug294" >A</a > <a href="#" class="selflink" >#</a @@ -147,9 +159,9 @@ ><p class="src" ><a id="v:problemField-39-" class="def" >problemField'</a - > :: DO <a href="#" + > :: DO <a href="#" title="Bug294" >A</a - > -> <a href="#" + > -> <a href="#" title="Bug294" >A</a > <a href="#" class="selflink" >#</a @@ -159,9 +171,9 @@ ><p class="src" ><a id="v:gadtField" class="def" >gadtField</a - > :: ({..} -> GADT <a href="#" + > :: GADT <a href="#" title="Bug294" >A</a - >) -> <a href="#" + > -> <a href="#" title="Bug294" >A</a > <a href="#" class="selflink" >#</a @@ -171,11 +183,69 @@ ><p class="src" ><span class="keyword" >data family</span + > <a id="t:TP" class="def" + >TP</a + > t :: * <a href="#" class="selflink" + >#</a + ></p + ><div class="subs instances" + ><details id="i:TP" open="open" + ><summary + >Instances</summary + ><table + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:if:TP:TP:1" + ></span + > <span class="keyword" + >data</span + > <a href="#" title="Bug294" + >TP</a + > <a href="#" title="Bug294" + >A</a + ></span + > <a href="#" class="selflink" + >#</a + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:if:TP:TP:1" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >Bug294</a + ></p + > <div class="src" + ><span class="keyword" + >data</span + > <a href="#" title="Bug294" + >TP</a + > <a href="#" title="Bug294" + >A</a + > = <a id="v:ProblemCtor" class="def" + >ProblemCtor</a + > <a href="#" title="Bug294" + >A</a + ></div + ></details + ></td + ></tr + ></table + ></details + ></div + ></div + ><div class="top" + ><p class="src" + ><span class="keyword" + >data family</span > <a id="t:DP" class="def" >DP</a - > t :: <a href="#" - >*</a - > <a href="#" class="selflink" + > t :: * <a href="#" class="selflink" >#</a ></p ><div class="subs instances" @@ -190,9 +260,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="Bug294" >DP</a - > <a href="#" + > <a href="#" title="Bug294" >A</a ></span > <a href="#" class="selflink" @@ -206,16 +276,20 @@ ><details id="i:if:DP:DP:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >Bug294</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="Bug294" >DP</a - > <a href="#" + > <a href="#" title="Bug294" >A</a > = <a id="v:ProblemCtor-39-" class="def" >ProblemCtor'</a - > <a href="#" + > <a href="#" title="Bug294" >A</a ></div ></details @@ -225,6 +299,60 @@ ></details ></div ></div + ><div class="top" + ><p class="src" + ><span class="keyword" + >data family</span + > <a id="t:TO-39-" class="def" + >TO'</a + > t :: * <a href="#" class="selflink" + >#</a + ></p + ><div class="subs instances" + ><details id="i:TO-39-" open="open" + ><summary + >Instances</summary + ><table + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:if:TO-39-:TO-39-:1" + ></span + > <span class="keyword" + >data</span + > <a href="#" title="Bug294" + >TO'</a + > a</span + > <a href="#" class="selflink" + >#</a + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:if:TO-39-:TO-39-:1" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >Bug294</a + ></p + > <div class="src" + ><span class="keyword" + >data</span + > <a href="#" title="Bug294" + >TO'</a + > a = <a id="v:PolyCtor" class="def" + >PolyCtor</a + ></div + ></details + ></td + ></tr + ></table + ></details + ></div + ></div ></div ></div ><div id="footer" diff --git a/html-test/ref/Bug298.html b/html-test/ref/Bug298.html index 532d40c5..94cb1533 100644 --- a/html-test/ref/Bug298.html +++ b/html-test/ref/Bug298.html @@ -111,19 +111,19 @@ ><div class="doc" ><p >Links to <code - ><a href="#" + ><a href="#" title="Bug298" ><^></a ></code > and <code - ><a href="#" + ><a href="#" title="Bug298" >^></a ></code >, <code - ><a href="#" + ><a href="#" title="Bug298" ><^</a ></code > and <code - ><a href="#" + ><a href="#" title="Bug298" >⋆^</a ></code >.</p diff --git a/html-test/ref/Bug3.html b/html-test/ref/Bug3.html index 80d01cfe..2c716278 100644 --- a/html-test/ref/Bug3.html +++ b/html-test/ref/Bug3.html @@ -46,9 +46,7 @@ ><li class="src short" ><a href="#" >foo</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div @@ -59,9 +57,7 @@ ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/Bug310.html b/html-test/ref/Bug310.html index 50ba8cfd..e664eccd 100644 --- a/html-test/ref/Bug310.html +++ b/html-test/ref/Bug310.html @@ -38,28 +38,6 @@ ><p class="caption" >Bug310</p ></div - ><div id="synopsis" - ><details id="syn" - ><summary - >Synopsis</summary - ><ul class="details-toggle" data-details-id="syn" - ><li class="src short" - ><span class="keyword" - >type family</span - > (a :: <a href="#" - >Nat</a - >) <a href="#" - >+</a - > (b :: <a href="#" - >Nat</a - >) :: <a href="#" - >Nat</a - > <span class="keyword" - >where ...</span - ></li - ></ul - ></details - ></div ><div id="interface" ><h1 >Documentation</h1 @@ -67,27 +45,13 @@ ><p class="src" ><span class="keyword" >type family</span - > (a :: <a href="#" - >Nat</a - >) <a id="t:-43-" class="def" + > (a :: Nat) <a id="t:-43-" class="def" >+</a - > (b :: <a href="#" - >Nat</a - >) :: <a href="#" - >Nat</a - > <span class="keyword" + > (b :: Nat) :: Nat <span class="keyword" >where ...</span - > <span class="fixity" - >infixl 6</span - ><span class="rightedge" - ></span > <a href="#" class="selflink" >#</a ></p - ><div class="doc" - ><p - >Addition of type-level naturals.</p - ></div ></div ></div ></div diff --git a/html-test/ref/Bug387.html b/html-test/ref/Bug387.html index 23faa420..da1b1ee5 100644 --- a/html-test/ref/Bug387.html +++ b/html-test/ref/Bug387.html @@ -60,44 +60,40 @@ ><li class="src short" ><a href="#" >test1</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >test2</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div ><div id="interface" - ><h1 id="g:1" - >Section1<a id="a:section1" + ><a href="#" id="g:1" + ><h1 + >Section1<a id="a:section1" + ></a + ></h1 ></a - ></h1 ><div class="top" ><p class="src" ><a id="v:test1" class="def" >test1</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ></div - ><h1 id="g:2" - >Section2<a id="a:section2" + ><a href="#" id="g:2" + ><h1 + >Section2<a id="a:section2" + ></a + ></h1 ></a - ></h1 ><div class="top" ><p class="src" ><a id="v:test2" class="def" >test2</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ></div diff --git a/html-test/ref/Bug4.html b/html-test/ref/Bug4.html index 40d9ee7b..6bf822f7 100644 --- a/html-test/ref/Bug4.html +++ b/html-test/ref/Bug4.html @@ -46,9 +46,7 @@ ><li class="src short" ><a href="#" >foo</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div @@ -59,9 +57,7 @@ ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/Bug458.html b/html-test/ref/Bug458.html new file mode 100644 index 00000000..f716d7d6 --- /dev/null +++ b/html-test/ref/Bug458.html @@ -0,0 +1,80 @@ +<html xmlns="http://www.w3.org/1999/xhtml" +><head + ><meta http-equiv="Content-Type" content="text/html; charset=UTF-8" + /><title + >Bug458</title + ><link href="#" rel="stylesheet" type="text/css" title="Ocean" + /><link rel="stylesheet" type="text/css" href="#" + /><script src="haddock-bundle.min.js" async="async" type="text/javascript" + ></script + ><script src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.0/MathJax.js?config=TeX-AMS-MML_HTMLorMML" type="text/javascript" + ></script + ></head + ><body + ><div id="package-header" + ><ul class="links" id="page-menu" + ><li + ><a href="#" + >Contents</a + ></li + ><li + ><a href="#" + >Index</a + ></li + ></ul + ><p class="caption empty" + ></p + ></div + ><div id="content" + ><div id="module-header" + ><table class="info" + ><tr + ><th + >Safe Haskell</th + ><td + >Safe</td + ></tr + ></table + ><p class="caption" + >Bug458</p + ></div + ><div id="synopsis" + ><details id="syn" + ><summary + >Synopsis</summary + ><ul class="details-toggle" data-details-id="syn" + ><li class="src short" + ><a href="#" + >(⊆)</a + > :: () -> () -> ()</li + ></ul + ></details + ></div + ><div id="interface" + ><h1 + >Documentation</h1 + ><div class="top" + ><p class="src" + ><a id="v:-8838-" class="def" + >(⊆)</a + > :: () -> () -> () <a href="#" class="selflink" + >#</a + ></p + ><div class="doc" + ><p + >See the defn of <code + ><code + ><a href="#" title="Bug458" + >⊆</a + ></code + ></code + >.</p + ></div + ></div + ></div + ></div + ><div id="footer" + ></div + ></body + ></html +>
\ No newline at end of file diff --git a/html-test/ref/Bug546.html b/html-test/ref/Bug546.html new file mode 100644 index 00000000..e2246475 --- /dev/null +++ b/html-test/ref/Bug546.html @@ -0,0 +1,261 @@ +<html xmlns="http://www.w3.org/1999/xhtml" +><head + ><meta http-equiv="Content-Type" content="text/html; charset=UTF-8" + /><title + >Bug546</title + ><link href="#" rel="stylesheet" type="text/css" title="Ocean" + /><link rel="stylesheet" type="text/css" href="#" + /><script src="haddock-bundle.min.js" async="async" type="text/javascript" + ></script + ><script src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.0/MathJax.js?config=TeX-AMS-MML_HTMLorMML" type="text/javascript" + ></script + ></head + ><body + ><div id="package-header" + ><ul class="links" id="page-menu" + ><li + ><a href="#" + >Contents</a + ></li + ><li + ><a href="#" + >Index</a + ></li + ></ul + ><p class="caption empty" + ></p + ></div + ><div id="content" + ><div id="module-header" + ><table class="info" + ><tr + ><th + >Safe Haskell</th + ><td + >Safe</td + ></tr + ></table + ><p class="caption" + >Bug546</p + ></div + ><div id="synopsis" + ><details id="syn" + ><summary + >Synopsis</summary + ><ul class="details-toggle" data-details-id="syn" + ><li class="src short" + ><a href="#" + >x</a + > :: Integer</li + ><li class="src short" + ><a href="#" + >compile</a + > :: String -> String</li + ></ul + ></details + ></div + ><div id="interface" + ><h1 + >Documentation</h1 + ><div class="top" + ><p class="src" + ><a id="v:x" class="def" + >x</a + > :: Integer <a href="#" class="selflink" + >#</a + ></p + ><div class="doc" + ><p + >Test:</p + ><dl + ><dt + ><code + >[code with square \ brackets]</code + ></dt + ><dd + >lorem ipsum</dd + ></dl + ></div + ></div + ><div class="top" + ><p class="src" + ><a id="v:compile" class="def" + >compile</a + > :: String -> String <a href="#" class="selflink" + >#</a + ></p + ><div class="doc" + ><dl + ><dt + ><code + >[..]</code + ></dt + ><dd + >Matches any of the enclosed characters. Ranges of characters can + be specified by separating the endpoints with a <code + >'-'</code + >. <code + >'-'</code + > or + <code + >']'</code + > can be matched by including them as the first character(s) + in the list. Never matches path separators: <code + >[/]</code + > matches + nothing at all. Named character classes can also be matched: + <code + >[:x:]</code + > within <code + >[]</code + > specifies the class named <code + >x</code + >, which matches + certain predefined characters. See below for a full list.</dd + ><dt + ><code + >[^..]</code + > or <code + >[!..]</code + ></dt + ><dd + >Like <code + >[..]</code + >, but matches any character <em + >not</em + > listed. + Note that <code + >[^-x]</code + > is not the inverse of <code + >[-x]</code + >, but + the range <code + >[^-x]</code + >.</dd + ><dt + ><code + ><m-n></code + ></dt + ><dd + >Matches any integer in the range m to n, inclusive. The range may + be open-ended by leaving out either number: <code + >"<->"</code + >, for + instance, matches any integer.</dd + ><dt + ><code + >**/</code + ></dt + ><dd + >Matches any number of characters, including path separators, + excluding the empty string.</dd + ></dl + ><p + >Supported character classes:</p + ><dl + ><dt + ><code + >[:alnum:]</code + ></dt + ><dd + >Equivalent to <code + >"0-9A-Za-z"</code + >.</dd + ><dt + ><code + >[:alpha:]</code + ></dt + ><dd + >Equivalent to <code + >"A-Za-z"</code + >.</dd + ><dt + ><code + >[:blank:]</code + ></dt + ><dd + >Equivalent to <code + >"\t "</code + >.</dd + ><dt + ><code + >[:cntrl:]</code + ></dt + ><dd + >Equivalent to <code + >"\0-\x1f\x7f"</code + >.</dd + ><dt + ><code + >[:digit:]</code + ></dt + ><dd + >Equivalent to <code + >"0-9"</code + >.</dd + ><dt + ><code + >[:graph:]</code + ></dt + ><dd + >Equivalent to <code + >"!-~"</code + >.</dd + ><dt + ><code + >[:lower:]</code + ></dt + ><dd + >Equivalent to <code + >"a-z"</code + >.</dd + ><dt + ><code + >[:print:]</code + ></dt + ><dd + >Equivalent to <code + >" -~"</code + >.</dd + ><dt + ><code + >[:punct:]</code + ></dt + ><dd + >Equivalent to <code + >"!-/:-@[-`{-~"</code + >.</dd + ><dt + ><code + >[:space:]</code + ></dt + ><dd + >Equivalent to <code + >"\t-\r "</code + >.</dd + ><dt + ><code + >[:upper:]</code + ></dt + ><dd + >Equivalent to <code + >"A-Z"</code + >.</dd + ><dt + ><code + >[:xdigit:]</code + ></dt + ><dd + >Equivalent to <code + >"0-9A-Fa-f"</code + >.</dd + ></dl + ></div + ></div + ></div + ></div + ><div id="footer" + ></div + ></body + ></html +>
\ No newline at end of file diff --git a/html-test/ref/Bug548.html b/html-test/ref/Bug548.html new file mode 100644 index 00000000..a8061eb2 --- /dev/null +++ b/html-test/ref/Bug548.html @@ -0,0 +1,450 @@ +<html xmlns="http://www.w3.org/1999/xhtml" +><head + ><meta http-equiv="Content-Type" content="text/html; charset=UTF-8" + /><title + >Bug548</title + ><link href="#" rel="stylesheet" type="text/css" title="Ocean" + /><link rel="stylesheet" type="text/css" href="#" + /><script src="haddock-bundle.min.js" async="async" type="text/javascript" + ></script + ><script src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.0/MathJax.js?config=TeX-AMS-MML_HTMLorMML" type="text/javascript" + ></script + ></head + ><body + ><div id="package-header" + ><ul class="links" id="page-menu" + ><li + ><a href="#" + >Contents</a + ></li + ><li + ><a href="#" + >Index</a + ></li + ></ul + ><p class="caption empty" + ></p + ></div + ><div id="content" + ><div id="module-header" + ><table class="info" + ><tr + ><th + >Safe Haskell</th + ><td + >Safe</td + ></tr + ></table + ><p class="caption" + >Bug548</p + ></div + ><div id="interface" + ><h1 + >Documentation</h1 + ><div class="top" + ><p class="src" + ><span class="keyword" + >newtype</span + > <a id="t:WrappedArrow" class="def" + >WrappedArrow</a + > (a :: * -> * -> *) b c <a href="#" class="selflink" + >#</a + ></p + ><div class="subs constructors" + ><p class="caption" + >Constructors</p + ><table + ><tr + ><td class="src" + ><a id="v:WrapArrow" class="def" + >WrapArrow</a + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><div class="subs fields" + ><p class="caption" + >Fields</p + ><ul + ><li + ><dfn class="src" + ><a id="v:unwrapArrow" class="def" + >unwrapArrow</a + > :: a b c</dfn + ><div class="doc empty" + ></div + ></li + ></ul + ></div + ></td + ></tr + ></table + ></div + ><div class="subs instances" + ><details id="i:WrappedArrow" open="open" + ><summary + >Instances</summary + ><table + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:WrappedArrow:Generic1:1" + ></span + > Generic1 (<a href="#" title="Bug548" + >WrappedArrow</a + > a b :: * -> *)</span + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:id:WrappedArrow:Generic1:1" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >Control.Applicative</a + ></p + > <div class="subs associated-types" + ><p class="caption" + >Associated Types</p + ><p class="src" + ><span class="keyword" + >type</span + > Rep1 (<a href="#" title="Bug548" + >WrappedArrow</a + > a b) :: k -> *</p + ></div + > <div class="subs methods" + ><p class="caption" + >Methods</p + ><p class="src" + ><a href="#" + >from1</a + > :: <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0 -> Rep1 (<a href="#" title="Bug548" + >WrappedArrow</a + > a b) a0</p + ><p class="src" + ><a href="#" + >to1</a + > :: Rep1 (<a href="#" title="Bug548" + >WrappedArrow</a + > a b) a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0</p + ></div + ></details + ></td + ></tr + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:WrappedArrow:Functor:2" + ></span + > Arrow a => Functor (<a href="#" title="Bug548" + >WrappedArrow</a + > a b)</span + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:id:WrappedArrow:Functor:2" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >Control.Applicative</a + ></p + > <div class="subs methods" + ><p class="caption" + >Methods</p + ><p class="src" + ><a href="#" + >fmap</a + > :: (a0 -> b0) -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b b0</p + ><p class="src" + ><a href="#" + >(<$)</a + > :: a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b b0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0</p + ></div + ></details + ></td + ></tr + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:WrappedArrow:Applicative:3" + ></span + > Arrow a => Applicative (<a href="#" title="Bug548" + >WrappedArrow</a + > a b)</span + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:id:WrappedArrow:Applicative:3" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >Control.Applicative</a + ></p + > <div class="subs methods" + ><p class="caption" + >Methods</p + ><p class="src" + ><a href="#" + >pure</a + > :: a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0</p + ><p class="src" + ><a href="#" + >(<*>)</a + > :: <a href="#" title="Bug548" + >WrappedArrow</a + > a b (a0 -> b0) -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b b0</p + ><p class="src" + ><a href="#" + >liftA2</a + > :: (a0 -> b0 -> c) -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b b0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b c</p + ><p class="src" + ><a href="#" + >(*>)</a + > :: <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b b0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b b0</p + ><p class="src" + ><a href="#" + >(<*)</a + > :: <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b b0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0</p + ></div + ></details + ></td + ></tr + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:WrappedArrow:Alternative:4" + ></span + > (ArrowZero a, ArrowPlus a) => Alternative (<a href="#" title="Bug548" + >WrappedArrow</a + > a b)</span + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:id:WrappedArrow:Alternative:4" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >Control.Applicative</a + ></p + > <div class="subs methods" + ><p class="caption" + >Methods</p + ><p class="src" + ><a href="#" + >empty</a + > :: <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0</p + ><p class="src" + ><a href="#" + >(<|>)</a + > :: <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0</p + ><p class="src" + ><a href="#" + >some</a + > :: <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b [a0]</p + ><p class="src" + ><a href="#" + >many</a + > :: <a href="#" title="Bug548" + >WrappedArrow</a + > a b a0 -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b [a0]</p + ></div + ></details + ></td + ></tr + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:WrappedArrow:Generic:5" + ></span + > Generic (<a href="#" title="Bug548" + >WrappedArrow</a + > a b c)</span + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:id:WrappedArrow:Generic:5" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >Control.Applicative</a + ></p + > <div class="subs associated-types" + ><p class="caption" + >Associated Types</p + ><p class="src" + ><span class="keyword" + >type</span + > Rep (<a href="#" title="Bug548" + >WrappedArrow</a + > a b c) :: * -> *</p + ></div + > <div class="subs methods" + ><p class="caption" + >Methods</p + ><p class="src" + ><a href="#" + >from</a + > :: <a href="#" title="Bug548" + >WrappedArrow</a + > a b c -> Rep (<a href="#" title="Bug548" + >WrappedArrow</a + > a b c) x</p + ><p class="src" + ><a href="#" + >to</a + > :: Rep (<a href="#" title="Bug548" + >WrappedArrow</a + > a b c) x -> <a href="#" title="Bug548" + >WrappedArrow</a + > a b c</p + ></div + ></details + ></td + ></tr + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:WrappedArrow:Rep1:6" + ></span + > <span class="keyword" + >type</span + > Rep1 (<a href="#" title="Bug548" + >WrappedArrow</a + > a b :: * -> *)</span + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:id:WrappedArrow:Rep1:6" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >Control.Applicative</a + ></p + > <div class="src" + ><span class="keyword" + >type</span + > Rep1 (<a href="#" title="Bug548" + >WrappedArrow</a + > a b :: * -> *) = D1 (MetaData "WrappedArrow" "Control.Applicative" "base" True) (C1 (MetaCons "WrapArrow" PrefixI True) (S1 (MetaSel (Just "unwrapArrow") NoSourceUnpackedness NoSourceStrictness DecidedLazy) (Rec1 (a b))))</div + ></details + ></td + ></tr + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:WrappedArrow:Rep:7" + ></span + > <span class="keyword" + >type</span + > Rep (<a href="#" title="Bug548" + >WrappedArrow</a + > a b c)</span + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:id:WrappedArrow:Rep:7" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >Control.Applicative</a + ></p + > <div class="src" + ><span class="keyword" + >type</span + > Rep (<a href="#" title="Bug548" + >WrappedArrow</a + > a b c) = D1 (MetaData "WrappedArrow" "Control.Applicative" "base" True) (C1 (MetaCons "WrapArrow" PrefixI True) (S1 (MetaSel (Just "unwrapArrow") NoSourceUnpackedness NoSourceStrictness DecidedLazy) (Rec0 (a b c))))</div + ></details + ></td + ></tr + ></table + ></details + ></div + ></div + ></div + ></div + ><div id="footer" + ></div + ></body + ></html +>
\ No newline at end of file diff --git a/html-test/ref/Bug6.html b/html-test/ref/Bug6.html index 9dc093cd..27f73d64 100644 --- a/html-test/ref/Bug6.html +++ b/html-test/ref/Bug6.html @@ -58,9 +58,7 @@ >A</a > = <a href="#" >A</a - > <a href="#" - >Int</a - ></li + > Int</li ><li class="src short" ><span class="keyword" >data</span @@ -68,15 +66,13 @@ >B</a > = <a href="#" >B</a - > {<ul class="subs" - ><li - ><a href="#" - >b</a - > :: <a href="#" - >Int</a - ></li - ></ul - >}</li + > Int</li + ><li class="src short" + ><a href="#" + >b</a + > :: <a href="#" title="Bug6" + >B</a + > -> Int</li ><li class="src short" ><span class="keyword" >data</span @@ -88,15 +84,11 @@ ><li ><a href="#" >c1</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li ><a href="#" >c2</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul >}</li ><li class="src short" @@ -106,11 +98,7 @@ >D</a > = <a href="#" >D</a - > <a href="#" - >Int</a - > <a href="#" - >Int</a - ></li + > Int Int</li ><li class="src short" ><span class="keyword" >newtype</span @@ -118,9 +106,7 @@ >E</a > = <a href="#" >E</a - > <a href="#" - >Int</a - ></li + > Int</li ></ul ></details ></div @@ -148,9 +134,7 @@ ><td class="src" ><a id="v:A" class="def" >A</a - > <a href="#" - >Int</a - ></td + > Int</td ><td class="doc empty" ></td ></tr @@ -179,35 +163,25 @@ ><td class="src" ><a id="v:B" class="def" >B</a - ></td + > Int</td ><td class="doc empty" ></td ></tr - ><tr - ><td colspan="2" - ><div class="subs fields" - ><p class="caption" - >Fields</p - ><ul - ><li - ><dfn class="src" - ><a id="v:b" class="def" - >b</a - > :: <a href="#" - >Int</a - ></dfn - ><div class="doc empty" - ></div - ></li - ></ul - ></div - ></td - ></tr ></table ></div ></div ><div class="top" ><p class="src" + ><a id="v:b" class="def" + >b</a + > :: <a href="#" title="Bug6" + >B</a + > -> Int <a href="#" class="selflink" + >#</a + ></p + ></div + ><div class="top" + ><p class="src" ><span class="keyword" >data</span > <a id="t:C" class="def" @@ -241,9 +215,7 @@ ><dfn class="src" ><a id="v:c1" class="def" >c1</a - > :: <a href="#" - >Int</a - ></dfn + > :: Int</dfn ><div class="doc empty" ></div ></li @@ -251,9 +223,7 @@ ><dfn class="src" ><a id="v:c2" class="def" >c2</a - > :: <a href="#" - >Int</a - ></dfn + > :: Int</dfn ><div class="doc empty" ></div ></li @@ -286,11 +256,7 @@ ><td class="src" ><a id="v:D" class="def" >D</a - > <a href="#" - >Int</a - > <a href="#" - >Int</a - ></td + > Int Int</td ><td class="doc empty" ></td ></tr @@ -318,9 +284,7 @@ ><td class="src" ><a id="v:E" class="def" >E</a - > <a href="#" - >Int</a - ></td + > Int</td ><td class="doc empty" ></td ></tr diff --git a/html-test/ref/Bug613.html b/html-test/ref/Bug613.html index 765f18e1..e8089fc8 100644 --- a/html-test/ref/Bug613.html +++ b/html-test/ref/Bug613.html @@ -51,7 +51,11 @@ > f <span class="keyword" >where</span ><ul class="subs" - ></ul + ><li + ><a href="#" + >fmap</a + > :: (a -> b) -> f a -> f b</li + ></ul ></li ><li class="src short" ><span class="keyword" @@ -78,14 +82,6 @@ > <a href="#" class="selflink" >#</a ></p - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >fmap</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p @@ -106,11 +102,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Functor:Functor:1" ></span - > <a href="#" + > <a href="#" title="Bug613" >Functor</a - > (<a href="#" - >Either</a - > a)</span + > (Either a)</span > <a href="#" class="selflink" >#</a ></td @@ -122,17 +116,17 @@ ><details id="i:ic:Functor:Functor:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Bug613</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >fmap</a - > :: (a0 -> b) -> <a href="#" - >Either</a - > a a0 -> <a href="#" - >Either</a - > a b <a href="#" class="selflink" + > :: (a0 -> b) -> Either a a0 -> Either a b <a href="#" class="selflink" >#</a ></p ></div @@ -144,9 +138,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Functor:Functor:2" ></span - > <a href="#" + > <a href="#" title="Bug613" >Functor</a - > (<a href="#" + > (<a href="#" title="Bug613" >ThreeVars</a > a0 a)</span > <a href="#" class="selflink" @@ -160,15 +154,19 @@ ><details id="i:ic:Functor:Functor:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Bug613</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >fmap</a - > :: (a1 -> b) -> <a href="#" + > :: (a1 -> b) -> <a href="#" title="Bug613" >ThreeVars</a - > a0 a a1 -> <a href="#" + > a0 a a1 -> <a href="#" title="Bug613" >ThreeVars</a > a0 a b <a href="#" class="selflink" >#</a @@ -218,9 +216,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:ThreeVars:Functor:1" ></span - > <a href="#" + > <a href="#" title="Bug613" >Functor</a - > (<a href="#" + > (<a href="#" title="Bug613" >ThreeVars</a > a0 a)</span > <a href="#" class="selflink" @@ -234,15 +232,19 @@ ><details id="i:id:ThreeVars:Functor:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Bug613</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >fmap</a - > :: (a1 -> b) -> <a href="#" + > :: (a1 -> b) -> <a href="#" title="Bug613" >ThreeVars</a - > a0 a a1 -> <a href="#" + > a0 a a1 -> <a href="#" title="Bug613" >ThreeVars</a > a0 a b <a href="#" class="selflink" >#</a diff --git a/html-test/ref/Bug647.html b/html-test/ref/Bug647.html index c35127f4..0928c1ec 100644 --- a/html-test/ref/Bug647.html +++ b/html-test/ref/Bug647.html @@ -52,14 +52,6 @@ > <a href="#" class="selflink" >#</a ></p - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >f</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p diff --git a/html-test/ref/Bug679.html b/html-test/ref/Bug679.html new file mode 100644 index 00000000..71eb9360 --- /dev/null +++ b/html-test/ref/Bug679.html @@ -0,0 +1,196 @@ +<html xmlns="http://www.w3.org/1999/xhtml" +><head + ><meta http-equiv="Content-Type" content="text/html; charset=UTF-8" + /><title + >Bug679</title + ><link href="#" rel="stylesheet" type="text/css" title="Ocean" + /><link rel="stylesheet" type="text/css" href="#" + /><script src="haddock-bundle.min.js" async="async" type="text/javascript" + ></script + ><script src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.0/MathJax.js?config=TeX-AMS-MML_HTMLorMML" type="text/javascript" + ></script + ></head + ><body + ><div id="package-header" + ><ul class="links" id="page-menu" + ><li + ><a href="#" + >Contents</a + ></li + ><li + ><a href="#" + >Index</a + ></li + ></ul + ><p class="caption empty" + ></p + ></div + ><div id="content" + ><div id="module-header" + ><table class="info" + ><tr + ><th + >Safe Haskell</th + ><td + >None</td + ></tr + ></table + ><p class="caption" + >Bug679</p + ></div + ><div id="interface" + ><h1 + >Documentation</h1 + ><div class="top" + ><p class="src" + ><span class="keyword" + >data</span + > <a id="t:Bar" class="def" + >Bar</a + > a <a href="#" class="selflink" + >#</a + ></p + ><div class="subs constructors" + ><p class="caption" + >Constructors</p + ><table + ><tr + ><td class="src" + ><a id="v:Bar" class="def" + >Bar</a + ></td + ><td class="doc empty" + ></td + ></tr + ></table + ></div + ><div class="subs instances" + ><details id="i:Bar" open="open" + ><summary + >Instances</summary + ><table + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:Bar:Foo:1" + ></span + > <a href="#" title="Bug679" + >Foo</a + > (<a href="#" title="Bug679" + >Bar</a + > a)</span + > <a href="#" class="selflink" + >#</a + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:id:Bar:Foo:1" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >Bug679</a + ></p + > <div class="subs methods" + ><p class="caption" + >Methods</p + ><p class="src" + ><a href="#" + >foo</a + > :: <a href="#" title="Bug679" + >Bar</a + > a -> <a href="#" title="Bug679" + >Bar</a + > a <a href="#" class="selflink" + >#</a + ></p + ></div + ></details + ></td + ></tr + ></table + ></details + ></div + ></div + ><div class="top" + ><p class="src" + ><span class="keyword" + >class</span + > <a id="t:Foo" class="def" + >Foo</a + > a <span class="keyword" + >where</span + > <a href="#" class="selflink" + >#</a + ></p + ><div class="subs methods" + ><p class="caption" + >Methods</p + ><p class="src" + ><a id="v:foo" class="def" + >foo</a + > :: a -> a <a href="#" class="selflink" + >#</a + ></p + ></div + ><div class="subs instances" + ><details id="i:Foo" open="open" + ><summary + >Instances</summary + ><table + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Foo:Foo:1" + ></span + > <a href="#" title="Bug679" + >Foo</a + > (<a href="#" title="Bug679" + >Bar</a + > a)</span + > <a href="#" class="selflink" + >#</a + ></td + ><td class="doc empty" + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:ic:Foo:Foo:1" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >Bug679</a + ></p + > <div class="subs methods" + ><p class="caption" + >Methods</p + ><p class="src" + ><a href="#" + >foo</a + > :: <a href="#" title="Bug679" + >Bar</a + > a -> <a href="#" title="Bug679" + >Bar</a + > a <a href="#" class="selflink" + >#</a + ></p + ></div + ></details + ></td + ></tr + ></table + ></details + ></div + ></div + ></div + ></div + ><div id="footer" + ></div + ></body + ></html +>
\ No newline at end of file diff --git a/html-test/ref/Bug7.html b/html-test/ref/Bug7.html index ba1a4e26..26a8e7a3 100644 --- a/html-test/ref/Bug7.html +++ b/html-test/ref/Bug7.html @@ -109,11 +109,11 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:Foo:Bar:1" ></span - > <a href="#" + > <a href="#" title="Bug7" >Bar</a - > <a href="#" + > <a href="#" title="Bug7" >Foo</a - > <a href="#" + > <a href="#" title="Bug7" >Foo</a ></span > <a href="#" class="selflink" @@ -129,6 +129,10 @@ ><details id="i:id:Foo:Bar:1" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >Bug7</a + ></p ></details ></td ></tr @@ -159,11 +163,11 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Bar:Bar:1" ></span - > <a href="#" + > <a href="#" title="Bug7" >Bar</a - > <a href="#" + > <a href="#" title="Bug7" >Foo</a - > <a href="#" + > <a href="#" title="Bug7" >Foo</a ></span > <a href="#" class="selflink" @@ -179,6 +183,10 @@ ><details id="i:ic:Bar:Bar:1" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >Bug7</a + ></p ></details ></td ></tr diff --git a/html-test/ref/Bug8.html b/html-test/ref/Bug8.html index 3149d919..7aa562f2 100644 --- a/html-test/ref/Bug8.html +++ b/html-test/ref/Bug8.html @@ -58,9 +58,9 @@ ><td class="src" ><a id="v:Type" class="def" >Type</a - > (<a href="#" + > (<a href="#" title="Bug8" >Typ</a - >, [<a href="#" + >, [<a href="#" title="Bug8" >Typ</a >])</td ><td class="doc empty" @@ -70,9 +70,9 @@ ><td class="src" ><a id="v:TFree" class="def" >TFree</a - > (<a href="#" + > (<a href="#" title="Bug8" >Typ</a - >, [<a href="#" + >, [<a href="#" title="Bug8" >Typ</a >])</td ><td class="doc empty" @@ -85,7 +85,7 @@ ><p class="src" ><a id="v:-45--45--62-" class="def" >(-->)</a - > :: p1 -> p2 -> <a href="#" + > :: p1 -> p2 -> <a href="#" title="Bug8" >Typ</a > <span class="fixity" >infix 9</span @@ -99,11 +99,9 @@ ><p class="src" ><a id="v:-45--45--45--62-" class="def" >(--->)</a - > :: <a href="#" - >Foldable</a - > t0 => t0 t -> <a href="#" + > :: Foldable t0 => t0 t -> <a href="#" title="Bug8" >Typ</a - > -> <a href="#" + > -> <a href="#" title="Bug8" >Typ</a > <span class="fixity" >infix 9</span diff --git a/html-test/ref/Bug85.html b/html-test/ref/Bug85.html index ee602f82..bf7e1465 100644 --- a/html-test/ref/Bug85.html +++ b/html-test/ref/Bug85.html @@ -47,15 +47,7 @@ >data</span > <a id="t:Foo" class="def" >Foo</a - > :: (<a href="#" - >*</a - > -> <a href="#" - >*</a - >) -> <a href="#" - >*</a - > -> <a href="#" - >*</a - > <span class="keyword" + > :: (* -> *) -> * -> * <span class="keyword" >where</span > <a href="#" class="selflink" >#</a @@ -68,7 +60,7 @@ ><td class="src" ><a id="v:Bar" class="def" >Bar</a - > :: f x -> <a href="#" + > :: f x -> <a href="#" title="Bug85" >Foo</a > f (f x)</td ><td class="doc empty" @@ -83,9 +75,7 @@ >data</span > <a id="t:Baz" class="def" >Baz</a - > :: <a href="#" - >*</a - > <span class="keyword" + > :: * <span class="keyword" >where</span > <a href="#" class="selflink" >#</a @@ -98,7 +88,7 @@ ><td class="src" ><a id="v:Baz-39-" class="def" >Baz'</a - > :: <a href="#" + > :: <a href="#" title="Bug85" >Baz</a ></td ><td class="doc empty" @@ -126,7 +116,7 @@ ><td class="src" ><a id="v:Quux" class="def" >Quux</a - > :: <a href="#" + > :: <a href="#" title="Bug85" >Qux</a ></td ><td class="doc empty" diff --git a/html-test/ref/BugDeprecated.html b/html-test/ref/BugDeprecated.html index ca801201..393a78ab 100644 --- a/html-test/ref/BugDeprecated.html +++ b/html-test/ref/BugDeprecated.html @@ -46,39 +46,27 @@ ><li class="src short" ><a href="#" >foo</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >bar</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >baz</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >one</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >two</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >three</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div @@ -89,9 +77,7 @@ ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -105,9 +91,7 @@ ><p class="src" ><a id="v:bar" class="def" >bar</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -121,9 +105,7 @@ ><p class="src" ><a id="v:baz" class="def" >baz</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -137,9 +119,7 @@ ><p class="src" ><a id="v:one" class="def" >one</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -155,9 +135,7 @@ ><p class="src" ><a id="v:two" class="def" >two</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -171,9 +149,7 @@ ><p class="src" ><a id="v:three" class="def" >three</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/BugExportHeadings.html b/html-test/ref/BugExportHeadings.html index 7b3e7728..17378531 100644 --- a/html-test/ref/BugExportHeadings.html +++ b/html-test/ref/BugExportHeadings.html @@ -76,88 +76,76 @@ ><li class="src short" ><a href="#" >foo</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >bar</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >baz</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >one</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >two</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >three</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div ><div id="interface" - ><h1 id="g:1" - >Foo</h1 + ><a href="#" id="g:1" + ><h1 + >Foo</h1 + ></a ><div class="top" ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ></div - ><h1 id="g:2" - >Bar</h1 + ><a href="#" id="g:2" + ><h1 + >Bar</h1 + ></a ><div class="top" ><p class="src" ><a id="v:bar" class="def" >bar</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ></div - ><h1 id="g:3" - >Baz</h1 + ><a href="#" id="g:3" + ><h1 + >Baz</h1 + ></a ><div class="top" ><p class="src" ><a id="v:baz" class="def" >baz</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ></div - ><h1 id="g:4" - >One</h1 + ><a href="#" id="g:4" + ><h1 + >One</h1 + ></a ><div class="top" ><p class="src" ><a id="v:one" class="def" >one</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -167,15 +155,15 @@ ></div ></div ></div - ><h1 id="g:5" - >Two</h1 + ><a href="#" id="g:5" + ><h1 + >Two</h1 + ></a ><div class="top" ><p class="src" ><a id="v:two" class="def" >two</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -185,15 +173,15 @@ ></div ></div ></div - ><h1 id="g:6" - >Three</h1 + ><a href="#" id="g:6" + ><h1 + >Three</h1 + ></a ><div class="top" ><p class="src" ><a id="v:three" class="def" >three</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/Bugs.html b/html-test/ref/Bugs.html index 8922fe9e..348ae6bc 100644 --- a/html-test/ref/Bugs.html +++ b/html-test/ref/Bugs.html @@ -58,9 +58,7 @@ ><td class="src" ><a id="v:A" class="def" >A</a - > a (a -> <a href="#" - >Int</a - >)</td + > a (a -> Int)</td ><td class="doc empty" ></td ></tr diff --git a/html-test/ref/BundledPatterns.html b/html-test/ref/BundledPatterns.html index dea60728..7a602ae1 100644 --- a/html-test/ref/BundledPatterns.html +++ b/html-test/ref/BundledPatterns.html @@ -48,19 +48,13 @@ >data</span > <a href="#" >Vec</a - > :: <a href="#" - >Nat</a - > -> <a href="#" - >*</a - > -> <a href="#" - >*</a - > <span class="keyword" + > :: Nat -> * -> * <span class="keyword" >where</span ><ul class="subs" ><li ><a href="#" >Nil</a - > :: <a href="#" + > :: <a href="#" title="BundledPatterns" >Vec</a > 0 a</li ><li @@ -68,11 +62,11 @@ >pattern</span > <a href="#" >(:>)</a - > :: a -> <a href="#" + > :: a -> <a href="#" title="BundledPatterns" >Vec</a - > n a -> <a href="#" + > n a -> <a href="#" title="BundledPatterns" >Vec</a - > (n <a href="#" + > (n <a href="#" title="Bug310" >+</a > 1) a</li ></ul @@ -82,13 +76,7 @@ >data</span > <a href="#" >RTree</a - > :: <a href="#" - >Nat</a - > -> <a href="#" - >*</a - > -> <a href="#" - >*</a - > <span class="keyword" + > :: Nat -> * -> * <span class="keyword" >where</span ><ul class="subs" ><li @@ -96,7 +84,7 @@ >pattern</span > <a href="#" >LR</a - > :: a -> <a href="#" + > :: a -> <a href="#" title="BundledPatterns" >RTree</a > 0 a</li ><li @@ -104,13 +92,13 @@ >pattern</span > <a href="#" >BR</a - > :: <a href="#" + > :: <a href="#" title="BundledPatterns" >RTree</a - > d a -> <a href="#" + > d a -> <a href="#" title="BundledPatterns" >RTree</a - > d a -> <a href="#" + > d a -> <a href="#" title="BundledPatterns" >RTree</a - > (d <a href="#" + > (d <a href="#" title="Bug310" >+</a > 1) a</li ></ul @@ -127,13 +115,7 @@ >data</span > <a id="t:Vec" class="def" >Vec</a - > :: <a href="#" - >Nat</a - > -> <a href="#" - >*</a - > -> <a href="#" - >*</a - > <span class="keyword" + > :: Nat -> * -> * <span class="keyword" >where</span > <a href="#" class="selflink" >#</a @@ -146,7 +128,7 @@ >Lists with their length encoded in their type</li ><li ><code - ><a href="#" + ><a href="#" title="BundledPatterns" >Vec</a ></code >tor elements have an <strong @@ -154,9 +136,7 @@ > subscript starting from 0 and ending at <code ><code - ><a href="#" - >length</a - ></code + >length</code > - 1</code >.</li ></ul @@ -169,7 +149,7 @@ ><td class="src" ><a id="v:Nil" class="def" >Nil</a - > :: <a href="#" + > :: <a href="#" title="BundledPatterns" >Vec</a > 0 a</td ><td class="doc empty" @@ -187,11 +167,11 @@ >pattern</span > <a id="v::-62-" class="def" >(:>)</a - > :: a -> <a href="#" + > :: a -> <a href="#" title="BundledPatterns" >Vec</a - > n a -> <a href="#" + > n a -> <a href="#" title="BundledPatterns" >Vec</a - > (n <a href="#" + > (n <a href="#" title="Bug310" >+</a > 1) a <span class="fixity" >infixr 5</span @@ -293,13 +273,7 @@ >data</span > <a id="t:RTree" class="def" >RTree</a - > :: <a href="#" - >Nat</a - > -> <a href="#" - >*</a - > -> <a href="#" - >*</a - > <span class="keyword" + > :: Nat -> * -> * <span class="keyword" >where</span > <a href="#" class="selflink" >#</a @@ -328,7 +302,7 @@ >pattern</span > <a id="v:LR" class="def" >LR</a - > :: a -> <a href="#" + > :: a -> <a href="#" title="BundledPatterns" >RTree</a > 0 a</td ><td class="doc" @@ -394,13 +368,13 @@ >pattern</span > <a id="v:BR" class="def" >BR</a - > :: <a href="#" + > :: <a href="#" title="BundledPatterns" >RTree</a - > d a -> <a href="#" + > d a -> <a href="#" title="BundledPatterns" >RTree</a - > d a -> <a href="#" + > d a -> <a href="#" title="BundledPatterns" >RTree</a - > (d <a href="#" + > (d <a href="#" title="Bug310" >+</a > 1) a</td ><td class="doc" diff --git a/html-test/ref/BundledPatterns2.html b/html-test/ref/BundledPatterns2.html index 385fd07f..6a60c748 100644 --- a/html-test/ref/BundledPatterns2.html +++ b/html-test/ref/BundledPatterns2.html @@ -48,35 +48,29 @@ >data</span > <a href="#" >Vec</a - > :: <a href="#" - >Nat</a - > -> <a href="#" - >*</a - > -> <a href="#" - >*</a - > <span class="keyword" + > :: Nat -> * -> * <span class="keyword" >where</span ><ul class="subs" ><li ><span class="keyword" >pattern</span > <a href="#" - >Empty</a - > :: <a href="#" + >(:>)</a + > :: a -> <a href="#" title="BundledPatterns2" >Vec</a - > 0 a</li + > n a -> <a href="#" title="BundledPatterns2" + >Vec</a + > (n <a href="#" title="Bug310" + >+</a + > 1) a</li ><li ><span class="keyword" >pattern</span > <a href="#" - >(:>)</a - > :: a -> <a href="#" - >Vec</a - > n a -> <a href="#" + >Empty</a + > :: <a href="#" title="BundledPatterns2" >Vec</a - > (n <a href="#" - >+</a - > 1) a</li + > 0 a</li ></ul ></li ><li class="src short" @@ -84,13 +78,7 @@ >data</span > <a href="#" >RTree</a - > :: <a href="#" - >Nat</a - > -> <a href="#" - >*</a - > -> <a href="#" - >*</a - > <span class="keyword" + > :: Nat -> * -> * <span class="keyword" >where</span ><ul class="subs" ><li @@ -98,7 +86,7 @@ >pattern</span > <a href="#" >LR</a - > :: a -> <a href="#" + > :: a -> <a href="#" title="BundledPatterns2" >RTree</a > 0 a</li ><li @@ -106,13 +94,13 @@ >pattern</span > <a href="#" >BR</a - > :: <a href="#" + > :: <a href="#" title="BundledPatterns2" >RTree</a - > d a -> <a href="#" + > d a -> <a href="#" title="BundledPatterns2" >RTree</a - > d a -> <a href="#" + > d a -> <a href="#" title="BundledPatterns2" >RTree</a - > (d <a href="#" + > (d <a href="#" title="Bug310" >+</a > 1) a</li ></ul @@ -129,13 +117,7 @@ >data</span > <a id="t:Vec" class="def" >Vec</a - > :: <a href="#" - >Nat</a - > -> <a href="#" - >*</a - > -> <a href="#" - >*</a - > <span class="keyword" + > :: Nat -> * -> * <span class="keyword" >where</span > <a href="#" class="selflink" >#</a @@ -148,7 +130,7 @@ >Lists with their length encoded in their type</li ><li ><code - ><a href="#" + ><a href="#" title="BundledPatterns2" >Vec</a ></code >tor elements have an <strong @@ -156,9 +138,7 @@ > subscript starting from 0 and ending at <code ><code - ><a href="#" - >length</a - ></code + >length</code > - 1</code >.</li ></ul @@ -171,25 +151,13 @@ ><td class="src" ><span class="keyword" >pattern</span - > <a id="v:Empty" class="def" - >Empty</a - > :: <a href="#" - >Vec</a - > 0 a</td - ><td class="doc empty" - ></td - ></tr - ><tr - ><td class="src" - ><span class="keyword" - >pattern</span > <a id="v::-62-" class="def" >(:>)</a - > :: a -> <a href="#" + > :: a -> <a href="#" title="BundledPatterns2" >Vec</a - > n a -> <a href="#" + > n a -> <a href="#" title="BundledPatterns2" >Vec</a - > (n <a href="#" + > (n <a href="#" title="Bug310" >+</a > 1) a <span class="fixity" >infixr 5</span @@ -282,6 +250,18 @@ </pre ></td ></tr + ><tr + ><td class="src" + ><span class="keyword" + >pattern</span + > <a id="v:Empty" class="def" + >Empty</a + > :: <a href="#" title="BundledPatterns2" + >Vec</a + > 0 a</td + ><td class="doc empty" + ></td + ></tr ></table ></div ></div @@ -291,13 +271,7 @@ >data</span > <a id="t:RTree" class="def" >RTree</a - > :: <a href="#" - >Nat</a - > -> <a href="#" - >*</a - > -> <a href="#" - >*</a - > <span class="keyword" + > :: Nat -> * -> * <span class="keyword" >where</span > <a href="#" class="selflink" >#</a @@ -326,7 +300,7 @@ >pattern</span > <a id="v:LR" class="def" >LR</a - > :: a -> <a href="#" + > :: a -> <a href="#" title="BundledPatterns2" >RTree</a > 0 a</td ><td class="doc" @@ -392,13 +366,13 @@ >pattern</span > <a id="v:BR" class="def" >BR</a - > :: <a href="#" + > :: <a href="#" title="BundledPatterns2" >RTree</a - > d a -> <a href="#" + > d a -> <a href="#" title="BundledPatterns2" >RTree</a - > d a -> <a href="#" + > d a -> <a href="#" title="BundledPatterns2" >RTree</a - > (d <a href="#" + > (d <a href="#" title="Bug310" >+</a > 1) a</td ><td class="doc" diff --git a/html-test/ref/ConstructorPatternExport.html b/html-test/ref/ConstructorPatternExport.html index 68e40a5a..548cd729 100644 --- a/html-test/ref/ConstructorPatternExport.html +++ b/html-test/ref/ConstructorPatternExport.html @@ -47,9 +47,7 @@ >pattern</span > <a id="v:FooCons" class="def" >FooCons</a - > :: <a href="#" - >String</a - > -> a -> Foo a <a href="#" class="selflink" + > :: String -> a -> Foo a <a href="#" class="selflink" >#</a ></p ></div @@ -59,11 +57,7 @@ >pattern</span > <a id="v:MyRecCons" class="def" >MyRecCons</a - > :: <a href="#" - >Bool</a - > -> <a href="#" - >Int</a - > -> MyRec <a href="#" class="selflink" + > :: Bool -> Int -> MyRec <a href="#" class="selflink" >#</a ></p ></div @@ -73,9 +67,7 @@ >pattern</span > <a id="v::-43-" class="def" >(:+)</a - > :: <a href="#" - >String</a - > -> a -> MyInfix a <a href="#" class="selflink" + > :: String -> a -> MyInfix a <a href="#" class="selflink" >#</a ></p ></div @@ -85,9 +77,7 @@ >pattern</span > <a id="v:BlubCons" class="def" >BlubCons</a - > :: () => <a href="#" - >Show</a - > b => b -> Blub <a href="#" class="selflink" + > :: () => Show b => b -> Blub <a href="#" class="selflink" >#</a ></p ></div @@ -97,17 +87,7 @@ >pattern</span > <a id="v:MyGADTCons" class="def" >MyGADTCons</a - > :: () => <span class="keyword" - >forall</span - > a. <a href="#" - >Eq</a - > a => a -> <a href="#" - >Int</a - > -> MyGADT (<a href="#" - >Maybe</a - > <a href="#" - >String</a - >) <a href="#" class="selflink" + > :: a -> Int -> MyGADT (Maybe String) <a href="#" class="selflink" >#</a ></p ></div diff --git a/html-test/ref/DeprecatedClass.html b/html-test/ref/DeprecatedClass.html index f7571316..55abc489 100644 --- a/html-test/ref/DeprecatedClass.html +++ b/html-test/ref/DeprecatedClass.html @@ -51,7 +51,11 @@ > a <span class="keyword" >where</span ><ul class="subs" - ></ul + ><li + ><a href="#" + >foo</a + > :: a -> a</li + ></ul ></li ><li class="src short" ><span class="keyword" @@ -61,7 +65,11 @@ > a <span class="keyword" >where</span ><ul class="subs" - ></ul + ><li + ><a href="#" + >bar</a + > :: a -> a</li + ></ul ></li ></ul ></details @@ -88,14 +96,6 @@ ><p >some class</p ></div - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >foo</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p @@ -132,14 +132,6 @@ >Deprecated: SomeOtherClass</p ></div ></div - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >bar</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p diff --git a/html-test/ref/DeprecatedFunction.html b/html-test/ref/DeprecatedFunction.html index 41bf7454..5682128f 100644 --- a/html-test/ref/DeprecatedFunction.html +++ b/html-test/ref/DeprecatedFunction.html @@ -46,15 +46,11 @@ ><li class="src short" ><a href="#" >foo</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >bar</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div @@ -65,16 +61,14 @@ ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" ><div class="warning" ><p >Deprecated: use <code - ><a href="#" + ><a href="#" title="DeprecatedFunction" >bar</a ></code > instead</p @@ -87,9 +81,7 @@ ><p class="src" ><a id="v:bar" class="def" >bar</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/DeprecatedFunction2.html b/html-test/ref/DeprecatedFunction2.html index bbf6cdd7..d4e19e7a 100644 --- a/html-test/ref/DeprecatedFunction2.html +++ b/html-test/ref/DeprecatedFunction2.html @@ -46,9 +46,7 @@ ><li class="src short" ><a href="#" >foo</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div @@ -59,9 +57,7 @@ ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/DeprecatedFunction3.html b/html-test/ref/DeprecatedFunction3.html index 96474a98..58cffae8 100644 --- a/html-test/ref/DeprecatedFunction3.html +++ b/html-test/ref/DeprecatedFunction3.html @@ -46,9 +46,7 @@ ><li class="src short" ><a href="#" >foo</a - > :: <a href="#" - >Integer</a - ></li + > :: Integer</li ></ul ></details ></div @@ -59,9 +57,7 @@ ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Integer</a - > <a href="#" class="selflink" + > :: Integer <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/DeprecatedModule.html b/html-test/ref/DeprecatedModule.html index 9971adb5..eb92dad9 100644 --- a/html-test/ref/DeprecatedModule.html +++ b/html-test/ref/DeprecatedModule.html @@ -61,9 +61,7 @@ ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ></div diff --git a/html-test/ref/DeprecatedModule2.html b/html-test/ref/DeprecatedModule2.html index 2e390b4f..81f2e024 100644 --- a/html-test/ref/DeprecatedModule2.html +++ b/html-test/ref/DeprecatedModule2.html @@ -55,9 +55,7 @@ ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ></div diff --git a/html-test/ref/DeprecatedNewtype.html b/html-test/ref/DeprecatedNewtype.html index c7803c81..2640cbb5 100644 --- a/html-test/ref/DeprecatedNewtype.html +++ b/html-test/ref/DeprecatedNewtype.html @@ -50,9 +50,7 @@ >SomeNewType</a > = <a href="#" >SomeNewTypeConst</a - > <a href="#" - >String</a - ></li + > String</li ><li class="src short" ><span class="keyword" >newtype</span @@ -60,9 +58,7 @@ >SomeOtherNewType</a > = <a href="#" >SomeOtherNewTypeConst</a - > <a href="#" - >String</a - ></li + > String</li ></ul ></details ></div @@ -94,9 +90,7 @@ ><td class="src" ><a id="v:SomeNewTypeConst" class="def" >SomeNewTypeConst</a - > <a href="#" - >String</a - ></td + > String</td ><td class="doc" ><div class="warning" ><p @@ -132,9 +126,7 @@ ><td class="src" ><a id="v:SomeOtherNewTypeConst" class="def" >SomeOtherNewTypeConst</a - > <a href="#" - >String</a - ></td + > String</td ><td class="doc" ><div class="warning" ><p diff --git a/html-test/ref/DeprecatedReExport.html b/html-test/ref/DeprecatedReExport.html index fd137108..214be4f4 100644 --- a/html-test/ref/DeprecatedReExport.html +++ b/html-test/ref/DeprecatedReExport.html @@ -72,29 +72,27 @@ ><li class="src short" ><a href="#" >foo</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div ><div id="interface" - ><h1 id="g:1" - >Re-exported from an other module</h1 + ><a href="#" id="g:1" + ><h1 + >Re-exported from an other module</h1 + ></a ><div class="top" ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" ><div class="warning" ><p >Deprecated: use <code - ><a href="#" + ><a href="#" title="DeprecatedFunction" >bar</a ></code > instead</p @@ -103,8 +101,10 @@ >some documentation for foo</p ></div ></div - ><h1 id="g:2" - >Re-exported from an other package</h1 + ><a href="#" id="g:2" + ><h1 + >Re-exported from an other package</h1 + ></a ><div class="doc" ><p >Not yet working, see <a href="#" diff --git a/html-test/ref/DeprecatedRecord.html b/html-test/ref/DeprecatedRecord.html index 3e2aa285..5ff532a4 100644 --- a/html-test/ref/DeprecatedRecord.html +++ b/html-test/ref/DeprecatedRecord.html @@ -54,15 +54,11 @@ ><li ><a href="#" >fooName</a - > :: <a href="#" - >String</a - ></li + > :: String</li ><li ><a href="#" >fooValue</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul >}</li ></ul @@ -106,9 +102,7 @@ ><dfn class="src" ><a id="v:fooName" class="def" >fooName</a - > :: <a href="#" - >String</a - ></dfn + > :: String</dfn ><div class="doc" ><p >some name</p @@ -118,9 +112,7 @@ ><dfn class="src" ><a id="v:fooValue" class="def" >fooValue</a - > :: <a href="#" - >Int</a - ></dfn + > :: Int</dfn ><div class="doc" ><div class="warning" ><p diff --git a/html-test/ref/DeprecatedTypeFamily.html b/html-test/ref/DeprecatedTypeFamily.html index 6f267c01..dab7683d 100644 --- a/html-test/ref/DeprecatedTypeFamily.html +++ b/html-test/ref/DeprecatedTypeFamily.html @@ -48,21 +48,13 @@ >data family</span > <a href="#" >SomeTypeFamily</a - > k :: <a href="#" - >*</a - > -> <a href="#" - >*</a - ></li + > k :: * -> *</li ><li class="src short" ><span class="keyword" >data family</span > <a href="#" >SomeOtherTypeFamily</a - > k :: <a href="#" - >*</a - > -> <a href="#" - >*</a - ></li + > k :: * -> *</li ></ul ></details ></div @@ -75,11 +67,7 @@ >data family</span > <a id="t:SomeTypeFamily" class="def" >SomeTypeFamily</a - > k :: <a href="#" - >*</a - > -> <a href="#" - >*</a - > <a href="#" class="selflink" + > k :: * -> * <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -97,11 +85,7 @@ >data family</span > <a id="t:SomeOtherTypeFamily" class="def" >SomeOtherTypeFamily</a - > k :: <a href="#" - >*</a - > -> <a href="#" - >*</a - > <a href="#" class="selflink" + > k :: * -> * <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/DeprecatedTypeSynonym.html b/html-test/ref/DeprecatedTypeSynonym.html index db0a8ab6..25526d72 100644 --- a/html-test/ref/DeprecatedTypeSynonym.html +++ b/html-test/ref/DeprecatedTypeSynonym.html @@ -48,17 +48,13 @@ >type</span > <a href="#" >TypeSyn</a - > = <a href="#" - >String</a - ></li + > = String</li ><li class="src short" ><span class="keyword" >type</span > <a href="#" >OtherTypeSyn</a - > = <a href="#" - >String</a - ></li + > = String</li ></ul ></details ></div @@ -71,9 +67,7 @@ >type</span > <a id="t:TypeSyn" class="def" >TypeSyn</a - > = <a href="#" - >String</a - > <a href="#" class="selflink" + > = String <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -91,9 +85,7 @@ >type</span > <a id="t:OtherTypeSyn" class="def" >OtherTypeSyn</a - > = <a href="#" - >String</a - > <a href="#" class="selflink" + > = String <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/Examples.html b/html-test/ref/Examples.html index fa321fab..7eeb5f7c 100644 --- a/html-test/ref/Examples.html +++ b/html-test/ref/Examples.html @@ -46,11 +46,7 @@ ><li class="src short" ><a href="#" >fib</a - > :: <a href="#" - >Integer</a - > -> <a href="#" - >Integer</a - ></li + > :: Integer -> Integer</li ></ul ></details ></div @@ -61,19 +57,13 @@ ><p class="src" ><a id="v:fib" class="def" >fib</a - > :: <a href="#" - >Integer</a - > -> <a href="#" - >Integer</a - > <a href="#" class="selflink" + > :: Integer -> Integer <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >Fibonacci number of given <code - ><a href="#" - >Integer</a - ></code + >Integer</code >.</p ><p >Examples:</p diff --git a/html-test/ref/FunArgs.html b/html-test/ref/FunArgs.html index 485f7e28..ae890105 100644 --- a/html-test/ref/FunArgs.html +++ b/html-test/ref/FunArgs.html @@ -54,17 +54,13 @@ ><table ><tr ><td class="src" - >:: <a href="#" - >Ord</a - > a</td + >:: Ord a</td ><td class="doc empty" ></td ></tr ><tr ><td class="src" - >=> <a href="#" - >Int</a - ></td + >=> Int</td ><td class="doc" ><p >First argument</p @@ -80,9 +76,7 @@ ></tr ><tr ><td class="src" - >-> <a href="#" - >Bool</a - ></td + >-> Bool</td ><td class="doc" ><p >Third argument</p @@ -214,9 +208,7 @@ ><td class="src" >:: <span class="keyword" >forall</span - > (b :: ()). d ~ <a href="#" - >()</a - ></td + > (b :: ()). d ~ ()</td ><td class="doc empty" ></td ></tr diff --git a/html-test/ref/GADTRecords.html b/html-test/ref/GADTRecords.html index bba54b3e..1f0c87e8 100644 --- a/html-test/ref/GADTRecords.html +++ b/html-test/ref/GADTRecords.html @@ -54,35 +54,27 @@ ><li ><a href="#" >C1</a - > :: <a href="#" + > :: <a href="#" title="GADTRecords" >H1</a > a b</li ><li ><a href="#" >C2</a - > :: <a href="#" - >Ord</a - > a => [a] -> <a href="#" + > :: Ord a => [a] -> <a href="#" title="GADTRecords" >H1</a > a a</li ><li ><a href="#" >C3</a - > :: {..} -> <a href="#" + > :: {..} -> <a href="#" title="GADTRecords" >H1</a - > <a href="#" - >Int</a - > <a href="#" - >Int</a - ></li + > Int Int</li ><li ><a href="#" >C4</a - > :: {..} -> <a href="#" + > :: {..} -> <a href="#" title="GADTRecords" >H1</a - > <a href="#" - >Int</a - > a</li + > Int a</li ></ul ></li ></ul @@ -114,7 +106,7 @@ ><td class="src" ><a id="v:C1" class="def" >C1</a - > :: <a href="#" + > :: <a href="#" title="GADTRecords" >H1</a > a b</td ><td class="doc empty" @@ -124,9 +116,7 @@ ><td class="src" ><a id="v:C2" class="def" >C2</a - > :: <a href="#" - >Ord</a - > a => [a] -> <a href="#" + > :: Ord a => [a] -> <a href="#" title="GADTRecords" >H1</a > a a</td ><td class="doc empty" @@ -136,12 +126,6 @@ ><td class="src" ><a id="v:C3" class="def" >C3</a - > :: {..} -> <a href="#" - >H1</a - > <a href="#" - >Int</a - > <a href="#" - >Int</a ></td ><td class="doc empty" ></td @@ -154,16 +138,22 @@ ><ul ><li ><dfn class="src" - ><a id="v:field" class="def" + >:: { <a id="v:field" class="def" >field</a - > :: <a href="#" - >Int</a - ></dfn + > :: Int</dfn ><div class="doc" ><p >hello docs</p ></div ></li + ><li + ><dfn class="src" + >} -> <a href="#" title="GADTRecords" + >H1</a + > Int Int</dfn + ><div class="doc empty" + ></div + ></li ></ul ></div ></td @@ -172,11 +162,7 @@ ><td class="src" ><a id="v:C4" class="def" >C4</a - > :: {..} -> <a href="#" - >H1</a - > <a href="#" - >Int</a - > a</td + ></td ><td class="doc empty" ></td ></tr @@ -188,7 +174,7 @@ ><ul ><li ><dfn class="src" - ><a id="v:field2" class="def" + >:: { <a id="v:field2" class="def" >field2</a > :: a</dfn ><div class="doc" @@ -196,6 +182,14 @@ >hello2 docs</p ></div ></li + ><li + ><dfn class="src" + >} -> <a href="#" title="GADTRecords" + >H1</a + > Int a</dfn + ><div class="doc empty" + ></div + ></li ></ul ></div ></td diff --git a/html-test/ref/Hash.html b/html-test/ref/Hash.html index 21004e20..c4f04f2c 100644 --- a/html-test/ref/Hash.html +++ b/html-test/ref/Hash.html @@ -87,37 +87,23 @@ ><li class="src short" ><a href="#" >new</a - > :: (<a href="#" - >Eq</a - > key, <a href="#" + > :: (Eq key, <a href="#" title="Hash" >Hash</a - > key) => <a href="#" - >Int</a - > -> <a href="#" - >IO</a - > (<a href="#" + > key) => Int -> IO (<a href="#" title="Hash" >HashTable</a > key val)</li ><li class="src short" ><a href="#" >insert</a - > :: (<a href="#" - >Eq</a - > key, <a href="#" + > :: (Eq key, <a href="#" title="Hash" >Hash</a - > key) => key -> val -> <a href="#" - >IO</a - > ()</li + > key) => key -> val -> IO ()</li ><li class="src short" ><a href="#" >lookup</a - > :: <a href="#" + > :: <a href="#" title="Hash" >Hash</a - > key => key -> <a href="#" - >IO</a - > (<a href="#" - >Maybe</a - > val)</li + > key => key -> IO (Maybe val)</li ><li class="src short" ><span class="keyword" >class</span @@ -126,16 +112,22 @@ > a <span class="keyword" >where</span ><ul class="subs" - ></ul + ><li + ><a href="#" + >hash</a + > :: a -> Int</li + ></ul ></li ></ul ></details ></div ><div id="interface" - ><h1 id="g:1" - >The <code - >HashTable</code - > type</h1 + ><a href="#" id="g:1" + ><h1 + >The <code + >HashTable</code + > type</h1 + ></a ><div class="top" ><p class="src" ><span class="keyword" @@ -155,29 +147,23 @@ The type <code >key</code > should be an instance of <code - ><a href="#" - >Eq</a - ></code + >Eq</code >.</p ></div ></div - ><h2 id="g:2" - >Operations on <code - >HashTable</code - >s</h2 + ><a href="#" id="g:2" + ><h2 + >Operations on <code + >HashTable</code + >s</h2 + ></a ><div class="top" ><p class="src" ><a id="v:new" class="def" >new</a - > :: (<a href="#" - >Eq</a - > key, <a href="#" + > :: (Eq key, <a href="#" title="Hash" >Hash</a - > key) => <a href="#" - >Int</a - > -> <a href="#" - >IO</a - > (<a href="#" + > key) => Int -> IO (<a href="#" title="Hash" >HashTable</a > key val) <a href="#" class="selflink" >#</a @@ -191,13 +177,9 @@ ><p class="src" ><a id="v:insert" class="def" >insert</a - > :: (<a href="#" - >Eq</a - > key, <a href="#" + > :: (Eq key, <a href="#" title="Hash" >Hash</a - > key) => key -> val -> <a href="#" - >IO</a - > () <a href="#" class="selflink" + > key) => key -> val -> IO () <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -209,35 +191,29 @@ ><p class="src" ><a id="v:lookup" class="def" >lookup</a - > :: <a href="#" + > :: <a href="#" title="Hash" >Hash</a - > key => key -> <a href="#" - >IO</a - > (<a href="#" - >Maybe</a - > val) <a href="#" class="selflink" + > key => key -> IO (Maybe val) <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >Looks up a key in the hash table, returns <code ><code - ><a href="#" - >Just</a - ></code + >Just</code > val</code > if the key was found, or <code - ><a href="#" - >Nothing</a - ></code + >Nothing</code > otherwise.</p ></div ></div - ><h1 id="g:3" - >The <code - >Hash</code - > class</h1 + ><a href="#" id="g:3" + ><h1 + >The <code + >Hash</code + > class</h1 + ></a ><div class="top" ><p class="src" ><span class="keyword" @@ -253,23 +229,13 @@ ><p >A class of types which can be hashed.</p ></div - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >hash</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a id="v:hash" class="def" >hash</a - > :: a -> <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: a -> Int <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -277,9 +243,7 @@ >hashes the value of type <code >a</code > into an <code - ><a href="#" - >Int</a - ></code + >Int</code ></p ></div ></div @@ -293,11 +257,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Hash:Hash:1" ></span - > <a href="#" + > <a href="#" title="Hash" >Hash</a - > <a href="#" - >Float</a - ></span + > Float</span > <a href="#" class="selflink" >#</a ></td @@ -309,17 +271,17 @@ ><details id="i:ic:Hash:Hash:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Hash</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >hash</a - > :: <a href="#" - >Float</a - > -> <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Float -> Int <a href="#" class="selflink" >#</a ></p ></div @@ -331,11 +293,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Hash:Hash:2" ></span - > <a href="#" + > <a href="#" title="Hash" >Hash</a - > <a href="#" - >Int</a - ></span + > Int</span > <a href="#" class="selflink" >#</a ></td @@ -347,17 +307,17 @@ ><details id="i:ic:Hash:Hash:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Hash</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >hash</a - > :: <a href="#" - >Int</a - > -> <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int -> Int <a href="#" class="selflink" >#</a ></p ></div @@ -369,11 +329,11 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Hash:Hash:3" ></span - > (<a href="#" + > (<a href="#" title="Hash" >Hash</a - > a, <a href="#" + > a, <a href="#" title="Hash" >Hash</a - > b) => <a href="#" + > b) => <a href="#" title="Hash" >Hash</a > (a, b)</span > <a href="#" class="selflink" @@ -387,15 +347,17 @@ ><details id="i:ic:Hash:Hash:3" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Hash</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >hash</a - > :: (a, b) -> <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: (a, b) -> Int <a href="#" class="selflink" >#</a ></p ></div diff --git a/html-test/ref/HiddenInstances.html b/html-test/ref/HiddenInstances.html index b3586649..eb39dafc 100644 --- a/html-test/ref/HiddenInstances.html +++ b/html-test/ref/HiddenInstances.html @@ -84,11 +84,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:VisibleClass:VisibleClass:1" ></span - > <a href="#" + > <a href="#" title="HiddenInstances" >VisibleClass</a - > <a href="#" - >Int</a - ></span + > Int</span > <a href="#" class="selflink" >#</a ></td @@ -102,6 +100,10 @@ ><details id="i:ic:VisibleClass:VisibleClass:1" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >HiddenInstances</a + ></p ></details ></td ></tr @@ -110,9 +112,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:VisibleClass:VisibleClass:2" ></span - > <a href="#" + > <a href="#" title="HiddenInstances" >VisibleClass</a - > <a href="#" + > <a href="#" title="HiddenInstances" >VisibleData</a ></span > <a href="#" class="selflink" @@ -128,6 +130,10 @@ ><details id="i:ic:VisibleClass:VisibleClass:2" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >HiddenInstances</a + ></p ></details ></td ></tr @@ -158,9 +164,7 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:VisibleData:Num:1" ></span - > <a href="#" - >Num</a - > <a href="#" + > Num <a href="#" title="HiddenInstances" >VisibleData</a ></span > <a href="#" class="selflink" @@ -176,84 +180,72 @@ ><details id="i:id:VisibleData:Num:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >HiddenInstances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >(+)</a - > :: <a href="#" + > :: <a href="#" title="HiddenInstances" >VisibleData</a - > -> <a href="#" + > -> <a href="#" title="HiddenInstances" >VisibleData</a - > -> <a href="#" + > -> <a href="#" title="HiddenInstances" >VisibleData</a - > <a href="#" class="selflink" - >#</a ></p ><p class="src" ><a href="#" >(-)</a - > :: <a href="#" + > :: <a href="#" title="HiddenInstances" >VisibleData</a - > -> <a href="#" + > -> <a href="#" title="HiddenInstances" >VisibleData</a - > -> <a href="#" + > -> <a href="#" title="HiddenInstances" >VisibleData</a - > <a href="#" class="selflink" - >#</a ></p ><p class="src" ><a href="#" >(*)</a - > :: <a href="#" + > :: <a href="#" title="HiddenInstances" >VisibleData</a - > -> <a href="#" + > -> <a href="#" title="HiddenInstances" >VisibleData</a - > -> <a href="#" + > -> <a href="#" title="HiddenInstances" >VisibleData</a - > <a href="#" class="selflink" - >#</a ></p ><p class="src" ><a href="#" >negate</a - > :: <a href="#" + > :: <a href="#" title="HiddenInstances" >VisibleData</a - > -> <a href="#" + > -> <a href="#" title="HiddenInstances" >VisibleData</a - > <a href="#" class="selflink" - >#</a ></p ><p class="src" ><a href="#" >abs</a - > :: <a href="#" + > :: <a href="#" title="HiddenInstances" >VisibleData</a - > -> <a href="#" + > -> <a href="#" title="HiddenInstances" >VisibleData</a - > <a href="#" class="selflink" - >#</a ></p ><p class="src" ><a href="#" >signum</a - > :: <a href="#" + > :: <a href="#" title="HiddenInstances" >VisibleData</a - > -> <a href="#" + > -> <a href="#" title="HiddenInstances" >VisibleData</a - > <a href="#" class="selflink" - >#</a ></p ><p class="src" ><a href="#" >fromInteger</a - > :: <a href="#" - >Integer</a - > -> <a href="#" + > :: Integer -> <a href="#" title="HiddenInstances" >VisibleData</a - > <a href="#" class="selflink" - >#</a ></p ></div ></details @@ -264,9 +256,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:VisibleData:VisibleClass:2" ></span - > <a href="#" + > <a href="#" title="HiddenInstances" >VisibleClass</a - > <a href="#" + > <a href="#" title="HiddenInstances" >VisibleData</a ></span > <a href="#" class="selflink" @@ -282,6 +274,10 @@ ><details id="i:id:VisibleData:VisibleClass:2" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >HiddenInstances</a + ></p ></details ></td ></tr diff --git a/html-test/ref/HiddenInstancesB.html b/html-test/ref/HiddenInstancesB.html index d2f7b74d..5b69947e 100644 --- a/html-test/ref/HiddenInstancesB.html +++ b/html-test/ref/HiddenInstancesB.html @@ -84,9 +84,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Foo:Foo:1" ></span - > <a href="#" + > <a href="#" title="HiddenInstancesB" >Foo</a - > <a href="#" + > <a href="#" title="HiddenInstancesB" >Bar</a ></span > <a href="#" class="selflink" @@ -102,6 +102,10 @@ ><details id="i:ic:Foo:Foo:1" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >HiddenInstancesA</a + ></p ></details ></td ></tr @@ -132,9 +136,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:Bar:Foo:1" ></span - > <a href="#" + > <a href="#" title="HiddenInstancesB" >Foo</a - > <a href="#" + > <a href="#" title="HiddenInstancesB" >Bar</a ></span > <a href="#" class="selflink" @@ -150,6 +154,10 @@ ><details id="i:id:Bar:Foo:1" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >HiddenInstancesA</a + ></p ></details ></td ></tr diff --git a/html-test/ref/Hyperlinks.html b/html-test/ref/Hyperlinks.html index 8e190358..58d012a5 100644 --- a/html-test/ref/Hyperlinks.html +++ b/html-test/ref/Hyperlinks.html @@ -46,9 +46,7 @@ ><li class="src short" ><a href="#" >foo</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div @@ -59,9 +57,7 @@ ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/ImplicitParams.html b/html-test/ref/ImplicitParams.html index 30e121b0..eb8456ae 100644 --- a/html-test/ref/ImplicitParams.html +++ b/html-test/ref/ImplicitParams.html @@ -69,9 +69,9 @@ ><p class="src" ><a id="v:c" class="def" >c</a - > :: (?x :: <a href="#" + > :: (?x :: <a href="#" title="ImplicitParams" >X</a - >) => <a href="#" + >) => <a href="#" title="ImplicitParams" >X</a > <a href="#" class="selflink" >#</a @@ -81,13 +81,13 @@ ><p class="src" ><a id="v:d" class="def" >d</a - > :: (?x :: <a href="#" + > :: (?x :: <a href="#" title="ImplicitParams" >X</a - >, ?y :: <a href="#" + >, ?y :: <a href="#" title="ImplicitParams" >X</a - >) => (<a href="#" + >) => (<a href="#" title="ImplicitParams" >X</a - >, <a href="#" + >, <a href="#" title="ImplicitParams" >X</a >) <a href="#" class="selflink" >#</a @@ -97,7 +97,7 @@ ><p class="src" ><a id="v:f" class="def" >f</a - > :: ((?x :: <a href="#" + > :: ((?x :: <a href="#" title="ImplicitParams" >X</a >) => a) -> a <a href="#" class="selflink" >#</a diff --git a/html-test/ref/Instances.html b/html-test/ref/Instances.html index 84c9498f..40b1045c 100644 --- a/html-test/ref/Instances.html +++ b/html-test/ref/Instances.html @@ -74,9 +74,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:-60--126--126-:Foo:1" ></span - > <a href="#" + > <a href="#" title="Instances" >Foo</a - > (<a href="#" + > (<a href="#" title="Instances" >(<~~)</a > a)</span > <a href="#" class="selflink" @@ -90,17 +90,19 @@ ><details id="i:id:-60--126--126-:Foo:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >foo</a - > :: (a <a href="#" + > :: (a <a href="#" title="Instances" ><~~</a - > <a href="#" - >Int</a - >) -> a0 -> a <a href="#" + > Int) -> a0 -> a <a href="#" title="Instances" ><~~</a > a0 <a href="#" class="selflink" >#</a @@ -108,19 +110,15 @@ ><p class="src" ><a href="#" >foo'</a - > :: (a <a href="#" + > :: (a <a href="#" title="Instances" ><~~</a - > (a <a href="#" + > (a <a href="#" title="Instances" ><~~</a - > a0)) -> <a href="#" - >Int</a - > -> a <a href="#" + > a0)) -> Int -> a <a href="#" title="Instances" ><~~</a - > (a <a href="#" + > (a <a href="#" title="Instances" ><~~</a - > <a href="#" - >Int</a - >) <a href="#" class="selflink" + > Int) <a href="#" class="selflink" >#</a ></p ></div @@ -142,25 +140,25 @@ > <a href="#" class="selflink" >#</a ></p + ><div class="subs minimal" + ><p class="caption" + >Minimal complete definition</p + ><p class="src" + >Nothing</p + ></div ><div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: f <a href="#" - >Int</a - > -> a -> f a <a href="#" class="selflink" + > :: f Int -> a -> f a <a href="#" class="selflink" >#</a ></p ><p class="src" ><a id="v:foo-39-" class="def" >foo'</a - > :: f (f a) -> <a href="#" - >Int</a - > -> f (f <a href="#" - >Int</a - >) <a href="#" class="selflink" + > :: f (f a) -> Int -> f (f Int) <a href="#" class="selflink" >#</a ></p ></div @@ -174,7 +172,7 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Foo:Foo:1" ></span - > <a href="#" + > <a href="#" title="Instances" >Foo</a > []</span > <a href="#" class="selflink" @@ -188,25 +186,23 @@ ><details id="i:ic:Foo:Foo:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >foo</a - > :: [<a href="#" - >Int</a - >] -> a -> [a] <a href="#" class="selflink" + > :: [Int] -> a -> [a] <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >foo'</a - > :: [[a]] -> <a href="#" - >Int</a - > -> [[<a href="#" - >Int</a - >]] <a href="#" class="selflink" + > :: [[a]] -> Int -> [[Int]] <a href="#" class="selflink" >#</a ></p ></div @@ -218,11 +214,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Foo:Foo:2" ></span - > <a href="#" + > <a href="#" title="Instances" >Foo</a - > <a href="#" - >Maybe</a - ></span + > Maybe</span > <a href="#" class="selflink" >#</a ></td @@ -234,37 +228,23 @@ ><details id="i:ic:Foo:Foo:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >foo</a - > :: <a href="#" - >Maybe</a - > <a href="#" - >Int</a - > -> a -> <a href="#" - >Maybe</a - > a <a href="#" class="selflink" + > :: Maybe Int -> a -> Maybe a <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >foo'</a - > :: <a href="#" - >Maybe</a - > (<a href="#" - >Maybe</a - > a) -> <a href="#" - >Int</a - > -> <a href="#" - >Maybe</a - > (<a href="#" - >Maybe</a - > <a href="#" - >Int</a - >) <a href="#" class="selflink" + > :: Maybe (Maybe a) -> Int -> Maybe (Maybe Int) <a href="#" class="selflink" >#</a ></p ></div @@ -276,11 +256,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Foo:Foo:3" ></span - > <a href="#" + > <a href="#" title="Instances" >Foo</a - > (<a href="#" - >Either</a - > a)</span + > (Either a)</span > <a href="#" class="selflink" >#</a ></td @@ -292,37 +270,23 @@ ><details id="i:ic:Foo:Foo:3" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >foo</a - > :: <a href="#" - >Either</a - > a <a href="#" - >Int</a - > -> a0 -> <a href="#" - >Either</a - > a a0 <a href="#" class="selflink" + > :: Either a Int -> a0 -> Either a a0 <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >foo'</a - > :: <a href="#" - >Either</a - > a (<a href="#" - >Either</a - > a a0) -> <a href="#" - >Int</a - > -> <a href="#" - >Either</a - > a (<a href="#" - >Either</a - > a <a href="#" - >Int</a - >) <a href="#" class="selflink" + > :: Either a (Either a a0) -> Int -> Either a (Either a Int) <a href="#" class="selflink" >#</a ></p ></div @@ -334,15 +298,11 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Foo:Foo:4" ></span - > (<a href="#" - >Eq</a - > a, <a href="#" + > (Eq a, <a href="#" title="Instances" >Foo</a - > f) => <a href="#" + > f) => <a href="#" title="Instances" >Foo</a - > (<a href="#" - >(,)</a - > (f a))</span + > ((,) (f a))</span > <a href="#" class="selflink" >#</a ></td @@ -354,25 +314,23 @@ ><details id="i:ic:Foo:Foo:4" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >foo</a - > :: (f a, <a href="#" - >Int</a - >) -> a0 -> (f a, a0) <a href="#" class="selflink" + > :: (f a, Int) -> a0 -> (f a, a0) <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >foo'</a - > :: (f a, (f a, a0)) -> <a href="#" - >Int</a - > -> (f a, (f a, <a href="#" - >Int</a - >)) <a href="#" class="selflink" + > :: (f a, (f a, a0)) -> Int -> (f a, (f a, Int)) <a href="#" class="selflink" >#</a ></p ></div @@ -384,9 +342,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Foo:Foo:5" ></span - > <a href="#" + > <a href="#" title="Instances" >Foo</a - > (<a href="#" + > (<a href="#" title="Instances" >(<~~)</a > a)</span > <a href="#" class="selflink" @@ -400,17 +358,19 @@ ><details id="i:ic:Foo:Foo:5" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >foo</a - > :: (a <a href="#" + > :: (a <a href="#" title="Instances" ><~~</a - > <a href="#" - >Int</a - >) -> a0 -> a <a href="#" + > Int) -> a0 -> a <a href="#" title="Instances" ><~~</a > a0 <a href="#" class="selflink" >#</a @@ -418,19 +378,15 @@ ><p class="src" ><a href="#" >foo'</a - > :: (a <a href="#" + > :: (a <a href="#" title="Instances" ><~~</a - > (a <a href="#" + > (a <a href="#" title="Instances" ><~~</a - > a0)) -> <a href="#" - >Int</a - > -> a <a href="#" + > a0)) -> Int -> a <a href="#" title="Instances" ><~~</a - > (a <a href="#" + > (a <a href="#" title="Instances" ><~~</a - > <a href="#" - >Int</a - >) <a href="#" class="selflink" + > Int) <a href="#" class="selflink" >#</a ></p ></div @@ -442,11 +398,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Foo:Foo:6" ></span - > <a href="#" + > <a href="#" title="Instances" >Foo</a - > (<a href="#" - >(,,)</a - > a a)</span + > ((,,) a a)</span > <a href="#" class="selflink" >#</a ></td @@ -458,25 +412,23 @@ ><details id="i:ic:Foo:Foo:6" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >foo</a - > :: (a, a, <a href="#" - >Int</a - >) -> a0 -> (a, a, a0) <a href="#" class="selflink" + > :: (a, a, Int) -> a0 -> (a, a, a0) <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >foo'</a - > :: (a, a, (a, a, a0)) -> <a href="#" - >Int</a - > -> (a, a, (a, a, <a href="#" - >Int</a - >)) <a href="#" class="selflink" + > :: (a, a, (a, a, a0)) -> Int -> (a, a, (a, a, Int)) <a href="#" class="selflink" >#</a ></p ></div @@ -488,9 +440,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Foo:Foo:7" ></span - > <a href="#" + > <a href="#" title="Instances" >Foo</a - > (<a href="#" + > (<a href="#" title="Instances" >Quux</a > a b)</span > <a href="#" class="selflink" @@ -504,17 +456,19 @@ ><details id="i:ic:Foo:Foo:7" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >foo</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Quux</a - > a b <a href="#" - >Int</a - > -> a0 -> <a href="#" + > a b Int -> a0 -> <a href="#" title="Instances" >Quux</a > a b a0 <a href="#" class="selflink" >#</a @@ -522,19 +476,15 @@ ><p class="src" ><a href="#" >foo'</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Quux</a - > a b (<a href="#" + > a b (<a href="#" title="Instances" >Quux</a - > a b a0) -> <a href="#" - >Int</a - > -> <a href="#" + > a b a0) -> Int -> <a href="#" title="Instances" >Quux</a - > a b (<a href="#" + > a b (<a href="#" title="Instances" >Quux</a - > a b <a href="#" - >Int</a - >) <a href="#" class="selflink" + > a b Int) <a href="#" class="selflink" >#</a ></p ></div @@ -546,13 +496,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Foo:Foo:8" ></span - > <a href="#" + > <a href="#" title="Instances" >Foo</a - > ((->) <a href="#" - >LiftedRep</a - > <a href="#" - >LiftedRep</a - > a)</span + > ((->) a :: * -> *)</span > <a href="#" class="selflink" >#</a ></td @@ -564,49 +510,23 @@ ><details id="i:ic:Foo:Foo:8" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >foo</a - > :: (<a href="#" - >LiftedRep</a - > -> <a href="#" - >LiftedRep</a - >) a <a href="#" - >Int</a - > -> a0 -> (<a href="#" - >LiftedRep</a - > -> <a href="#" - >LiftedRep</a - >) a a0 <a href="#" class="selflink" + > :: (a -> Int) -> a0 -> a -> a0 <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >foo'</a - > :: (<a href="#" - >LiftedRep</a - > -> <a href="#" - >LiftedRep</a - >) a ((<a href="#" - >LiftedRep</a - > -> <a href="#" - >LiftedRep</a - >) a a0) -> <a href="#" - >Int</a - > -> (<a href="#" - >LiftedRep</a - > -> <a href="#" - >LiftedRep</a - >) a ((<a href="#" - >LiftedRep</a - > -> <a href="#" - >LiftedRep</a - >) a <a href="#" - >Int</a - >) <a href="#" class="selflink" + > :: (a -> (a -> a0)) -> Int -> a -> (a -> Int) <a href="#" class="selflink" >#</a ></p ></div @@ -621,7 +541,7 @@ ><p class="src" ><span class="keyword" >class</span - > <a href="#" + > <a href="#" title="Instances" >Foo</a > f => <a id="t:Bar" class="def" >Bar</a @@ -630,15 +550,19 @@ > <a href="#" class="selflink" >#</a ></p + ><div class="subs minimal" + ><p class="caption" + >Minimal complete definition</p + ><p class="src" + >Nothing</p + ></div ><div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a id="v:bar" class="def" >bar</a - > :: f a -> f <a href="#" - >Bool</a - > -> a <a href="#" class="selflink" + > :: f a -> f Bool -> a <a href="#" class="selflink" >#</a ></p ><p class="src" @@ -670,13 +594,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Bar:Bar:1" ></span - > <a href="#" + > <a href="#" title="Instances" >Bar</a - > <a href="#" - >Maybe</a - > <a href="#" - >Bool</a - ></span + > Maybe Bool</span > <a href="#" class="selflink" >#</a ></td @@ -688,77 +608,35 @@ ><details id="i:ic:Bar:Bar:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >bar</a - > :: <a href="#" - >Maybe</a - > <a href="#" - >Bool</a - > -> <a href="#" - >Maybe</a - > <a href="#" - >Bool</a - > -> <a href="#" - >Bool</a - > <a href="#" class="selflink" + > :: Maybe Bool -> Maybe Bool -> Bool <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >bar'</a - > :: <a href="#" - >Maybe</a - > (<a href="#" - >Maybe</a - > <a href="#" - >Bool</a - >) -> <a href="#" - >Maybe</a - > (<a href="#" - >Maybe</a - > (<a href="#" - >Maybe</a - > b)) <a href="#" class="selflink" + > :: Maybe (Maybe Bool) -> Maybe (Maybe (Maybe b)) <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >bar0</a - > :: (<a href="#" - >Maybe</a - > <a href="#" - >Bool</a - >, <a href="#" - >Maybe</a - > <a href="#" - >Bool</a - >) -> (<a href="#" - >Maybe</a - > b, <a href="#" - >Maybe</a - > c) <a href="#" class="selflink" + > :: (Maybe Bool, Maybe Bool) -> (Maybe b, Maybe c) <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >bar1</a - > :: (<a href="#" - >Maybe</a - > <a href="#" - >Bool</a - >, <a href="#" - >Maybe</a - > <a href="#" - >Bool</a - >) -> (<a href="#" - >Maybe</a - > b, <a href="#" - >Maybe</a - > c) <a href="#" class="selflink" + > :: (Maybe Bool, Maybe Bool) -> (Maybe b, Maybe c) <a href="#" class="selflink" >#</a ></p ></div @@ -770,11 +648,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Bar:Bar:2" ></span - > <a href="#" + > <a href="#" title="Instances" >Bar</a - > <a href="#" - >Maybe</a - > [a]</span + > Maybe [a]</span > <a href="#" class="selflink" >#</a ></td @@ -786,63 +662,35 @@ ><details id="i:ic:Bar:Bar:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >bar</a - > :: <a href="#" - >Maybe</a - > [a] -> <a href="#" - >Maybe</a - > <a href="#" - >Bool</a - > -> [a] <a href="#" class="selflink" + > :: Maybe [a] -> Maybe Bool -> [a] <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >bar'</a - > :: <a href="#" - >Maybe</a - > (<a href="#" - >Maybe</a - > [a]) -> <a href="#" - >Maybe</a - > (<a href="#" - >Maybe</a - > (<a href="#" - >Maybe</a - > b)) <a href="#" class="selflink" + > :: Maybe (Maybe [a]) -> Maybe (Maybe (Maybe b)) <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >bar0</a - > :: (<a href="#" - >Maybe</a - > [a], <a href="#" - >Maybe</a - > [a]) -> (<a href="#" - >Maybe</a - > b, <a href="#" - >Maybe</a - > c) <a href="#" class="selflink" + > :: (Maybe [a], Maybe [a]) -> (Maybe b, Maybe c) <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >bar1</a - > :: (<a href="#" - >Maybe</a - > [a], <a href="#" - >Maybe</a - > [a]) -> (<a href="#" - >Maybe</a - > b, <a href="#" - >Maybe</a - > c) <a href="#" class="selflink" + > :: (Maybe [a], Maybe [a]) -> (Maybe b, Maybe c) <a href="#" class="selflink" >#</a ></p ></div @@ -854,7 +702,7 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Bar:Bar:3" ></span - > <a href="#" + > <a href="#" title="Instances" >Bar</a > [] (a, a)</span > <a href="#" class="selflink" @@ -868,15 +716,17 @@ ><details id="i:ic:Bar:Bar:3" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >bar</a - > :: [(a, a)] -> [<a href="#" - >Bool</a - >] -> (a, a) <a href="#" class="selflink" + > :: [(a, a)] -> [Bool] -> (a, a) <a href="#" class="selflink" >#</a ></p ><p class="src" @@ -906,13 +756,11 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Bar:Bar:4" ></span - > <a href="#" + > <a href="#" title="Instances" >Foo</a - > f => <a href="#" + > f => <a href="#" title="Instances" >Bar</a - > (<a href="#" - >Either</a - > a) (f a)</span + > (Either a) (f a)</span > <a href="#" class="selflink" >#</a ></td @@ -924,63 +772,35 @@ ><details id="i:ic:Bar:Bar:4" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >bar</a - > :: <a href="#" - >Either</a - > a (f a) -> <a href="#" - >Either</a - > a <a href="#" - >Bool</a - > -> f a <a href="#" class="selflink" + > :: Either a (f a) -> Either a Bool -> f a <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >bar'</a - > :: <a href="#" - >Either</a - > a (<a href="#" - >Either</a - > a (f a)) -> <a href="#" - >Either</a - > a (<a href="#" - >Either</a - > a (<a href="#" - >Either</a - > a b)) <a href="#" class="selflink" + > :: Either a (Either a (f a)) -> Either a (Either a (Either a b)) <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >bar0</a - > :: (<a href="#" - >Either</a - > a (f a), <a href="#" - >Either</a - > a (f a)) -> (<a href="#" - >Either</a - > a b, <a href="#" - >Either</a - > a c) <a href="#" class="selflink" + > :: (Either a (f a), Either a (f a)) -> (Either a b, Either a c) <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >bar1</a - > :: (<a href="#" - >Either</a - > a (f a), <a href="#" - >Either</a - > a (f a)) -> (<a href="#" - >Either</a - > a b, <a href="#" - >Either</a - > a c) <a href="#" class="selflink" + > :: (Either a (f a), Either a (f a)) -> (Either a b, Either a c) <a href="#" class="selflink" >#</a ></p ></div @@ -992,15 +812,11 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Bar:Bar:5" ></span - > <a href="#" + > <a href="#" title="Instances" >Foo</a - > (<a href="#" - >(,,)</a - > a b) => <a href="#" + > ((,,) a b) => <a href="#" title="Instances" >Bar</a - > (<a href="#" - >(,,)</a - > a b) (a, b, a)</span + > ((,,) a b) (a, b, a)</span > <a href="#" class="selflink" >#</a ></td @@ -1012,15 +828,17 @@ ><details id="i:ic:Bar:Bar:5" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >bar</a - > :: (a, b, (a, b, a)) -> (a, b, <a href="#" - >Bool</a - >) -> (a, b, a) <a href="#" class="selflink" + > :: (a, b, (a, b, a)) -> (a, b, Bool) -> (a, b, a) <a href="#" class="selflink" >#</a ></p ><p class="src" @@ -1050,11 +868,11 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Bar:Bar:6" ></span - > <a href="#" + > <a href="#" title="Instances" >Bar</a - > (<a href="#" + > (<a href="#" title="Instances" >Quux</a - > a c) (<a href="#" + > a c) (<a href="#" title="Instances" >Quux</a > a b c)</span > <a href="#" class="selflink" @@ -1068,21 +886,23 @@ ><details id="i:ic:Bar:Bar:6" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >bar</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c) -> <a href="#" + > a b c) -> <a href="#" title="Instances" >Quux</a - > a c <a href="#" - >Bool</a - > -> <a href="#" + > a c Bool -> <a href="#" title="Instances" >Quux</a > a b c <a href="#" class="selflink" >#</a @@ -1090,17 +910,17 @@ ><p class="src" ><a href="#" >bar'</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c)) -> <a href="#" + > a b c)) -> <a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a > a c b0)) <a href="#" class="selflink" >#</a @@ -1108,17 +928,17 @@ ><p class="src" ><a href="#" >bar0</a - > :: (<a href="#" + > :: (<a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c), <a href="#" + > a b c), <a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c)) -> (<a href="#" + > a b c)) -> (<a href="#" title="Instances" >Quux</a - > a c b0, <a href="#" + > a c b0, <a href="#" title="Instances" >Quux</a > a c c0) <a href="#" class="selflink" >#</a @@ -1126,17 +946,17 @@ ><p class="src" ><a href="#" >bar1</a - > :: (<a href="#" + > :: (<a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c), <a href="#" + > a b c), <a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c)) -> (<a href="#" + > a b c)) -> (<a href="#" title="Instances" >Quux</a - > a c b0, <a href="#" + > a c b0, <a href="#" title="Instances" >Quux</a > a c c0) <a href="#" class="selflink" >#</a @@ -1160,6 +980,12 @@ > <a href="#" class="selflink" >#</a ></p + ><div class="subs minimal" + ><p class="caption" + >Minimal complete definition</p + ><p class="src" + >Nothing</p + ></div ><div class="subs methods" ><p class="caption" >Methods</p @@ -1206,7 +1032,7 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Baz:Baz:1" ></span - > <a href="#" + > <a href="#" title="Instances" >Baz</a > [c]</span > <a href="#" class="selflink" @@ -1220,7 +1046,11 @@ ><details id="i:ic:Baz:Baz:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" @@ -1264,7 +1094,7 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Baz:Baz:2" ></span - > <a href="#" + > <a href="#" title="Instances" >Baz</a > (a -> b)</span > <a href="#" class="selflink" @@ -1278,7 +1108,11 @@ ><details id="i:ic:Baz:Baz:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" @@ -1322,7 +1156,7 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Baz:Baz:3" ></span - > <a href="#" + > <a href="#" title="Instances" >Baz</a > (a, b, c)</span > <a href="#" class="selflink" @@ -1336,7 +1170,11 @@ ><details id="i:ic:Baz:Baz:3" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" @@ -1380,9 +1218,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Baz:Baz:4" ></span - > <a href="#" + > <a href="#" title="Instances" >Baz</a - > (<a href="#" + > (<a href="#" title="Instances" >Quux</a > a b c)</span > <a href="#" class="selflink" @@ -1396,19 +1234,23 @@ ><details id="i:ic:Baz:Baz:4" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >baz</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Quux</a > a b c -> (<span class="keyword" >forall</span > a0. a0 -> a0) -> (b0, <span class="keyword" >forall</span - > c0. c0 -> <a href="#" + > c0. c0 -> <a href="#" title="Instances" >Quux</a > a b c) -> (b0, c1) <a href="#" class="selflink" >#</a @@ -1418,13 +1260,13 @@ >baz'</a > :: b0 -> (<span class="keyword" >forall</span - > b1. b1 -> <a href="#" + > b1. b1 -> <a href="#" title="Instances" >Quux</a > a b c) -> (<span class="keyword" >forall</span - > b2. b2 -> <a href="#" + > b2. b2 -> <a href="#" title="Instances" >Quux</a - > a b c) -> [(b0, <a href="#" + > a b c) -> [(b0, <a href="#" title="Instances" >Quux</a > a b c)] <a href="#" class="selflink" >#</a @@ -1436,7 +1278,7 @@ >forall</span > b1. (<span class="keyword" >forall</span - > b2. b2 -> <a href="#" + > b2. b2 -> <a href="#" title="Instances" >Quux</a > a b c) -> c0) -> <span class="keyword" >forall</span @@ -1452,7 +1294,7 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Baz:Baz:5" ></span - > <a href="#" + > <a href="#" title="Instances" >Baz</a > (a, [b], b, a)</span > <a href="#" class="selflink" @@ -1466,7 +1308,11 @@ ><details id="i:ic:Baz:Baz:5" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" @@ -1558,9 +1404,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:Quux:Foo:1" ></span - > <a href="#" + > <a href="#" title="Instances" >Foo</a - > (<a href="#" + > (<a href="#" title="Instances" >Quux</a > a b)</span > <a href="#" class="selflink" @@ -1574,17 +1420,19 @@ ><details id="i:id:Quux:Foo:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >foo</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Quux</a - > a b <a href="#" - >Int</a - > -> a0 -> <a href="#" + > a b Int -> a0 -> <a href="#" title="Instances" >Quux</a > a b a0 <a href="#" class="selflink" >#</a @@ -1592,19 +1440,15 @@ ><p class="src" ><a href="#" >foo'</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Quux</a - > a b (<a href="#" + > a b (<a href="#" title="Instances" >Quux</a - > a b a0) -> <a href="#" - >Int</a - > -> <a href="#" + > a b a0) -> Int -> <a href="#" title="Instances" >Quux</a - > a b (<a href="#" + > a b (<a href="#" title="Instances" >Quux</a - > a b <a href="#" - >Int</a - >) <a href="#" class="selflink" + > a b Int) <a href="#" class="selflink" >#</a ></p ></div @@ -1616,11 +1460,11 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:Quux:Bar:2" ></span - > <a href="#" + > <a href="#" title="Instances" >Bar</a - > (<a href="#" + > (<a href="#" title="Instances" >Quux</a - > a c) (<a href="#" + > a c) (<a href="#" title="Instances" >Quux</a > a b c)</span > <a href="#" class="selflink" @@ -1634,21 +1478,23 @@ ><details id="i:id:Quux:Bar:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >bar</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c) -> <a href="#" + > a b c) -> <a href="#" title="Instances" >Quux</a - > a c <a href="#" - >Bool</a - > -> <a href="#" + > a c Bool -> <a href="#" title="Instances" >Quux</a > a b c <a href="#" class="selflink" >#</a @@ -1656,17 +1502,17 @@ ><p class="src" ><a href="#" >bar'</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c)) -> <a href="#" + > a b c)) -> <a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a > a c b0)) <a href="#" class="selflink" >#</a @@ -1674,17 +1520,17 @@ ><p class="src" ><a href="#" >bar0</a - > :: (<a href="#" + > :: (<a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c), <a href="#" + > a b c), <a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c)) -> (<a href="#" + > a b c)) -> (<a href="#" title="Instances" >Quux</a - > a c b0, <a href="#" + > a c b0, <a href="#" title="Instances" >Quux</a > a c c0) <a href="#" class="selflink" >#</a @@ -1692,17 +1538,17 @@ ><p class="src" ><a href="#" >bar1</a - > :: (<a href="#" + > :: (<a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c), <a href="#" + > a b c), <a href="#" title="Instances" >Quux</a - > a c (<a href="#" + > a c (<a href="#" title="Instances" >Quux</a - > a b c)) -> (<a href="#" + > a b c)) -> (<a href="#" title="Instances" >Quux</a - > a c b0, <a href="#" + > a c b0, <a href="#" title="Instances" >Quux</a > a c c0) <a href="#" class="selflink" >#</a @@ -1716,9 +1562,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:Quux:Baz:3" ></span - > <a href="#" + > <a href="#" title="Instances" >Baz</a - > (<a href="#" + > (<a href="#" title="Instances" >Quux</a > a b c)</span > <a href="#" class="selflink" @@ -1732,19 +1578,23 @@ ><details id="i:id:Quux:Baz:3" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >baz</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Quux</a > a b c -> (<span class="keyword" >forall</span > a0. a0 -> a0) -> (b0, <span class="keyword" >forall</span - > c0. c0 -> <a href="#" + > c0. c0 -> <a href="#" title="Instances" >Quux</a > a b c) -> (b0, c1) <a href="#" class="selflink" >#</a @@ -1754,13 +1604,13 @@ >baz'</a > :: b0 -> (<span class="keyword" >forall</span - > b1. b1 -> <a href="#" + > b1. b1 -> <a href="#" title="Instances" >Quux</a > a b c) -> (<span class="keyword" >forall</span - > b2. b2 -> <a href="#" + > b2. b2 -> <a href="#" title="Instances" >Quux</a - > a b c) -> [(b0, <a href="#" + > a b c) -> [(b0, <a href="#" title="Instances" >Quux</a > a b c)] <a href="#" class="selflink" >#</a @@ -1772,7 +1622,7 @@ >forall</span > b1. (<span class="keyword" >forall</span - > b2. b2 -> <a href="#" + > b2. b2 -> <a href="#" title="Instances" >Quux</a > a b c) -> c0) -> <span class="keyword" >forall</span @@ -1790,11 +1640,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="Instances" >Thud</a - > <a href="#" - >Int</a - > (<a href="#" + > Int (<a href="#" title="Instances" >Quux</a > a [a] c)</span > <a href="#" class="selflink" @@ -1808,14 +1656,16 @@ ><details id="i:id:Quux:Thud:4" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="Instances" >Thud</a - > <a href="#" - >Int</a - > (<a href="#" + > Int (<a href="#" title="Instances" >Quux</a > a [a] c) <ul class="inst" ><li class="inst" @@ -1825,11 +1675,7 @@ ><li class="inst" >| <a id="v:Thuuud" class="def" >Thuuud</a - > <a href="#" - >Int</a - > <a href="#" - >Int</a - ></li + > Int Int</li ></ul ></div ></details @@ -1850,6 +1696,12 @@ > <a href="#" class="selflink" >#</a ></p + ><div class="subs minimal" + ><p class="caption" + >Minimal complete definition</p + ><p class="src" + >Nothing</p + ></div ><div class="subs associated-types" ><p class="caption" >Associated Types</p @@ -1876,7 +1728,7 @@ ><p class="src" ><a id="v:norf" class="def" >norf</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Plugh</a > a c b -> a -> (a -> c) -> b <a href="#" class="selflink" >#</a @@ -1892,13 +1744,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Norf:Norf:1" ></span - > <a href="#" + > <a href="#" title="Instances" >Norf</a - > <a href="#" - >Int</a - > <a href="#" - >Bool</a - ></span + > Int Bool</span > <a href="#" class="selflink" >#</a ></td @@ -1910,33 +1758,27 @@ ><details id="i:ic:Norf:Norf:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs associated-types" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs associated-types" ><p class="caption" >Associated Types</p ><p class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="Instances" >Plugh</a - > <a href="#" - >Int</a - > c <a href="#" - >Bool</a - > :: <a href="#" - >*</a - > <a href="#" class="selflink" + > Int c Bool :: * <a href="#" class="selflink" >#</a ></p ><p class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="Instances" >Thud</a - > <a href="#" - >Int</a - > c :: <a href="#" - >*</a - > <a href="#" class="selflink" + > Int c :: * <a href="#" class="selflink" >#</a ></p ></div @@ -1946,19 +1788,9 @@ ><p class="src" ><a href="#" >norf</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Plugh</a - > <a href="#" - >Int</a - > c <a href="#" - >Bool</a - > -> <a href="#" - >Int</a - > -> (<a href="#" - >Int</a - > -> c) -> <a href="#" - >Bool</a - > <a href="#" class="selflink" + > Int c Bool -> Int -> (Int -> c) -> Bool <a href="#" class="selflink" >#</a ></p ></div @@ -1970,7 +1802,7 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Norf:Norf:2" ></span - > <a href="#" + > <a href="#" title="Instances" >Norf</a > [a] [b]</span > <a href="#" class="selflink" @@ -1984,27 +1816,27 @@ ><details id="i:ic:Norf:Norf:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs associated-types" + ><p + >Defined in <a href="#" + >Instances</a + ></p + > <div class="subs associated-types" ><p class="caption" >Associated Types</p ><p class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="Instances" >Plugh</a - > [a] c [b] :: <a href="#" - >*</a - > <a href="#" class="selflink" + > [a] c [b] :: * <a href="#" class="selflink" >#</a ></p ><p class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="Instances" >Thud</a - > [a] c :: <a href="#" - >*</a - > <a href="#" class="selflink" + > [a] c :: * <a href="#" class="selflink" >#</a ></p ></div @@ -2014,7 +1846,7 @@ ><p class="src" ><a href="#" >norf</a - > :: <a href="#" + > :: <a href="#" title="Instances" >Plugh</a > [a] c [b] -> [a] -> ([a] -> c) -> [b] <a href="#" class="selflink" >#</a diff --git a/html-test/ref/Math.html b/html-test/ref/Math.html index 33ac0239..ebdf6385 100644 --- a/html-test/ref/Math.html +++ b/html-test/ref/Math.html @@ -62,9 +62,7 @@ ><li class="src short" ><a href="#" >f</a - > :: <a href="#" - >Integer</a - ></li + > :: Integer</li ></ul ></details ></div @@ -75,9 +73,7 @@ ><p class="src" ><a id="v:f" class="def" >f</a - > :: <a href="#" - >Integer</a - > <a href="#" class="selflink" + > :: Integer <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/Minimal.html b/html-test/ref/Minimal.html index d7797a06..bc2da115 100644 --- a/html-test/ref/Minimal.html +++ b/html-test/ref/Minimal.html @@ -64,19 +64,19 @@ ><p class="caption" >Minimal complete definition</p ><p class="src" - ><a href="#" + ><a href="#" title="Minimal" >foo</a - >, <a href="#" + >, <a href="#" title="Minimal" >bar</a - > | <a href="#" + > | <a href="#" title="Minimal" >bar</a - >, <a href="#" + >, <a href="#" title="Minimal" >bat</a - > | <a href="#" + > | <a href="#" title="Minimal" >foo</a - >, <a href="#" + >, <a href="#" title="Minimal" >bat</a - > | <a href="#" + > | <a href="#" title="Minimal" >fooBarBat</a ></p ></div @@ -128,6 +128,26 @@ > <a href="#" class="selflink" >#</a ></p + ><div class="subs minimal" + ><p class="caption" + >Minimal complete definition</p + ><p class="src" + >(<a href="#" title="Minimal" + >a</a + >, <a href="#" title="Minimal" + >b</a + >, <a href="#" title="Minimal" + >c</a + > | (<a href="#" title="Minimal" + >d</a + > | <a href="#" title="Minimal" + >e</a + >, (<a href="#" title="Minimal" + >f</a + > | <a href="#" title="Minimal" + >g</a + >)))</p + ></div ><div class="subs methods" ><p class="caption" >Methods</p @@ -190,9 +210,9 @@ ><p class="caption" >Minimal complete definition</p ><p class="src" - ><a href="#" + ><a href="#" title="Minimal" >x</a - >, <a href="#" + >, <a href="#" title="Minimal" >y</a ></p ></div @@ -230,16 +250,6 @@ > <a href="#" class="selflink" >#</a ></p - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >aaa</a - >, <a href="#" - >bbb</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p @@ -272,7 +282,7 @@ ><p class="caption" >Minimal complete definition</p ><p class="src" - ><a href="#" + ><a href="#" title="Minimal" >ccc</a >, ddd</p ></div @@ -298,6 +308,12 @@ > <a href="#" class="selflink" >#</a ></p + ><div class="subs minimal" + ><p class="caption" + >Minimal complete definition</p + ><p class="src" + >Nothing</p + ></div ><div class="subs methods" ><p class="caption" >Methods</p diff --git a/html-test/ref/ModuleWithWarning.html b/html-test/ref/ModuleWithWarning.html index 12d98122..c29b20d9 100644 --- a/html-test/ref/ModuleWithWarning.html +++ b/html-test/ref/ModuleWithWarning.html @@ -61,9 +61,7 @@ ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ></div diff --git a/html-test/ref/NoLayout.html b/html-test/ref/NoLayout.html index 607b5f8d..1f908ba3 100644 --- a/html-test/ref/NoLayout.html +++ b/html-test/ref/NoLayout.html @@ -46,9 +46,7 @@ ><li class="src short" ><a href="#" >g</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div @@ -59,15 +57,13 @@ ><p class="src" ><a id="v:g" class="def" >g</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >the function <code - ><a href="#" + ><a href="#" title="NoLayout" >g</a ></code ></p diff --git a/html-test/ref/Operators.html b/html-test/ref/Operators.html index 1db0a91a..d01038a3 100644 --- a/html-test/ref/Operators.html +++ b/html-test/ref/Operators.html @@ -70,19 +70,19 @@ >Foo</a ><ul class="subs" ><li - >= <a href="#" + >= <a href="#" title="Operators" >Foo</a > <a href="#" >`Bar`</a - > <a href="#" + > <a href="#" title="Operators" >Foo</a ></li ><li - >| <a href="#" + >| <a href="#" title="Operators" >Foo</a > <a href="#" >:-</a - > <a href="#" + > <a href="#" title="Operators" >Foo</a ></li ></ul @@ -106,7 +106,7 @@ ><li ><a href="#" >(:<->)</a - > :: a -> b -> a <a href="#" + > :: a -> b -> a <a href="#" title="Operators" ><-></a > b</li ></ul @@ -136,15 +136,29 @@ >type</span > a <a href="#" ><><</a - > b :: <a href="#" - >*</a - ></li + > b :: *</li ><li ><span class="keyword" >data</span > a <a href="#" >><<</a > b</li + ><li + ><a href="#" + >(>><)</a + >, <a href="#" + >(<<>)</a + > :: a -> b -> ()</li + ><li + ><a href="#" + >(**>)</a + >, <a href="#" + >(**<)</a + >, <a href="#" + >(>**)</a + >, <a href="#" + >(<**)</a + > :: a -> a -> ()</li ></ul ></li ><li class="src short" @@ -152,7 +166,7 @@ >type</span > <a href="#" >(>-<)</a - > a b = a <a href="#" + > a b = a <a href="#" title="Operators" ><-></a > b</li ></ul @@ -224,11 +238,11 @@ ><table ><tr ><td class="src" - ><a href="#" + ><a href="#" title="Operators" >Foo</a > <a id="v:Bar" class="def" >`Bar`</a - > <a href="#" + > <a href="#" title="Operators" >Foo</a > <span class="fixity" >infixl 3</span @@ -242,11 +256,11 @@ ></tr ><tr ><td class="src" - ><a href="#" + ><a href="#" title="Operators" >Foo</a > <a id="v::-45-" class="def" >:-</a - > <a href="#" + > <a href="#" title="Operators" >Foo</a > <span class="fixity" >infixr 5</span @@ -308,7 +322,7 @@ ><td class="src" ><a id="v::-60--45--62-" class="def" >(:<->)</a - > :: a -> b -> a <a href="#" + > :: a -> b -> a <a href="#" title="Operators" ><-></a > b <span class="fixity" >infixr 6</span @@ -376,24 +390,6 @@ ><p >Class with fixity, including associated types</p ></div - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >(>><)</a - >, <a href="#" - >(<<>)</a - >, <a href="#" - >(**>)</a - >, <a href="#" - >(**<)</a - >, <a href="#" - >(>**)</a - >, <a href="#" - >(<**)</a - ></p - ></div ><div class="subs associated-types" ><p class="caption" >Associated Types</p @@ -402,9 +398,7 @@ >type</span > a <a id="t:-60--62--60-" class="def" ><><</a - > b :: <a href="#" - >*</a - > <span class="fixity" + > b :: * <span class="fixity" >infixl 2</span ><span class="rightedge" ></span @@ -511,7 +505,7 @@ >type</span > <a id="t:-62--45--60-" class="def" >(>-<)</a - > a b = a <a href="#" + > a b = a <a href="#" title="Operators" ><-></a > b <span class="fixity" >infixl 6</span diff --git a/html-test/ref/OrphanInstances.html b/html-test/ref/OrphanInstances.html index b7fa346c..a70c9640 100644 --- a/html-test/ref/OrphanInstances.html +++ b/html-test/ref/OrphanInstances.html @@ -48,18 +48,8 @@ ></li ></ul ></div - ><div id="synopsis" - ><details id="syn" - ><summary - >Synopsis</summary - ><ul class="details-toggle" data-details-id="syn" - ></ul - ></details - ></div ><div id="interface" ><h1 - >Documentation</h1 - ><h1 >Orphan instances</h1 ><div id="section.orphans" ><table @@ -68,9 +58,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:o:ic:AClass:AClass:1" ></span - > <a href="#" + > <a href="#" title="OrphanInstancesClass" >AClass</a - > <a href="#" + > <a href="#" title="OrphanInstancesType" >AType</a ></span > <a href="#" class="selflink" @@ -86,17 +76,17 @@ ><details id="i:o:ic:AClass:AClass:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >aClass</a - > :: <a href="#" + > :: <a href="#" title="OrphanInstancesType" >AType</a - > -> <a href="#" - >Int</a - > <a href="#" class="selflink" + > -> Int <a href="#" class="selflink" >#</a ></p ></div diff --git a/html-test/ref/OrphanInstancesClass.html b/html-test/ref/OrphanInstancesClass.html index 1fc2f112..c59c43dd 100644 --- a/html-test/ref/OrphanInstancesClass.html +++ b/html-test/ref/OrphanInstancesClass.html @@ -52,26 +52,66 @@ > <a href="#" class="selflink" >#</a ></p - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >aClass</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a id="v:aClass" class="def" >aClass</a - > :: a -> <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: a -> Int <a href="#" class="selflink" >#</a ></p ></div + ><div class="subs instances" + ><details id="i:AClass" open="open" + ><summary + >Instances</summary + ><table + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:AClass:AClass:1" + ></span + > <a href="#" title="OrphanInstancesClass" + >AClass</a + > <a href="#" title="OrphanInstancesType" + >AType</a + ></span + > <a href="#" class="selflink" + >#</a + ></td + ><td class="doc" + ><p + >This is an orphan instance.</p + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:ic:AClass:AClass:1" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >OrphanInstances</a + ></p + > <div class="subs methods" + ><p class="caption" + >Methods</p + ><p class="src" + ><a href="#" + >aClass</a + > :: <a href="#" title="OrphanInstancesType" + >AType</a + > -> Int <a href="#" class="selflink" + >#</a + ></p + ></div + ></details + ></td + ></tr + ></table + ></details + ></div ></div ></div ></div diff --git a/html-test/ref/OrphanInstancesType.html b/html-test/ref/OrphanInstancesType.html index d5998efe..2714bb1f 100644 --- a/html-test/ref/OrphanInstancesType.html +++ b/html-test/ref/OrphanInstancesType.html @@ -58,14 +58,62 @@ ><td class="src" ><a id="v:AType" class="def" >AType</a - > <a href="#" - >Int</a - ></td + > Int</td ><td class="doc empty" ></td ></tr ></table ></div + ><div class="subs instances" + ><details id="i:AType" open="open" + ><summary + >Instances</summary + ><table + ><tr + ><td class="src clearfix" + ><span class="inst-left" + ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:AType:AClass:1" + ></span + > <a href="#" title="OrphanInstancesClass" + >AClass</a + > <a href="#" title="OrphanInstancesType" + >AType</a + ></span + > <a href="#" class="selflink" + >#</a + ></td + ><td class="doc" + ><p + >This is an orphan instance.</p + ></td + ></tr + ><tr + ><td colspan="2" + ><details id="i:id:AType:AClass:1" + ><summary class="hide-when-js-enabled" + >Instance details</summary + ><p + >Defined in <a href="#" + >OrphanInstances</a + ></p + > <div class="subs methods" + ><p class="caption" + >Methods</p + ><p class="src" + ><a href="#" + >aClass</a + > :: <a href="#" title="OrphanInstancesType" + >AType</a + > -> Int <a href="#" class="selflink" + >#</a + ></p + ></div + ></details + ></td + ></tr + ></table + ></details + ></div ></div ></div ></div diff --git a/html-test/ref/PatternSyns.html b/html-test/ref/PatternSyns.html index bf0cdf1e..fce20f96 100644 --- a/html-test/ref/PatternSyns.html +++ b/html-test/ref/PatternSyns.html @@ -66,7 +66,7 @@ >Foo</a > :: <span class="keyword" >forall</span - > x. x -> <a href="#" + > x. x -> <a href="#" title="PatternSyns" >FooType</a > x</li ><li class="src short" @@ -76,9 +76,9 @@ >Bar</a > :: <span class="keyword" >forall</span - > x. x -> <a href="#" + > x. x -> <a href="#" title="PatternSyns" >FooType</a - > (<a href="#" + > (<a href="#" title="PatternSyns" >FooType</a > x)</li ><li class="src short" @@ -88,11 +88,11 @@ >(:<->)</a > :: <span class="keyword" >forall</span - > x x1. x -> x1 -> (<a href="#" + > x x1. x -> x1 -> (<a href="#" title="PatternSyns" >FooType</a - > x, <a href="#" + > x, <a href="#" title="PatternSyns" >FooType</a - > (<a href="#" + > (<a href="#" title="PatternSyns" >FooType</a > x1))</li ><li class="src short" @@ -100,9 +100,7 @@ >data</span > <a href="#" >BlubType</a - > = <a href="#" - >Show</a - > x => <a href="#" + > = Show x => <a href="#" >BlubCtor</a > x</li ><li class="src short" @@ -112,17 +110,13 @@ >Blub</a > :: () => <span class="keyword" >forall</span - > x. <a href="#" - >Show</a - > x => x -> <a href="#" + > x. Show x => x -> <a href="#" title="PatternSyns" >BlubType</a ></li ><li class="src short" ><span class="keyword" >data</span - > (a :: <a href="#" - >*</a - >) <a href="#" + > (a :: *) <a href="#" >><</a > b = <a href="#" >Empty</a @@ -134,17 +128,15 @@ >E</a > :: <span class="keyword" >forall</span - > k a (b :: k). <a href="#" - >(><)</a - > k a b</li + > k a (b :: k). a <a href="#" title="PatternSyns" + >><</a + > b</li ><li class="src short" ><span class="keyword" >pattern</span > <a href="#" >PatWithExplicitSig</a - > :: <a href="#" - >Eq</a - > somex => somex -> <a href="#" + > :: Eq somex => somex -> <a href="#" title="PatternSyns" >FooType</a > somex</li ></ul @@ -189,7 +181,7 @@ >Foo</a > :: <span class="keyword" >forall</span - > x. x -> <a href="#" + > x. x -> <a href="#" title="PatternSyns" >FooType</a > x <a href="#" class="selflink" >#</a @@ -197,7 +189,7 @@ ><div class="doc" ><p >Pattern synonym for <code - ><a href="#" + ><a href="#" title="PatternSyns" >Foo</a ></code > x</p @@ -211,9 +203,9 @@ >Bar</a > :: <span class="keyword" >forall</span - > x. x -> <a href="#" + > x. x -> <a href="#" title="PatternSyns" >FooType</a - > (<a href="#" + > (<a href="#" title="PatternSyns" >FooType</a > x) <a href="#" class="selflink" >#</a @@ -221,7 +213,7 @@ ><div class="doc" ><p >Pattern synonym for <code - ><a href="#" + ><a href="#" title="PatternSyns" >Bar</a ></code > x</p @@ -235,11 +227,11 @@ >(:<->)</a > :: <span class="keyword" >forall</span - > x x1. x -> x1 -> (<a href="#" + > x x1. x -> x1 -> (<a href="#" title="PatternSyns" >FooType</a - > x, <a href="#" + > x, <a href="#" title="PatternSyns" >FooType</a - > (<a href="#" + > (<a href="#" title="PatternSyns" >FooType</a > x1)) <a href="#" class="selflink" >#</a @@ -247,7 +239,7 @@ ><div class="doc" ><p >Pattern synonym for (<code - ><a href="#" + ><a href="#" title="PatternSyns" >:<-></a ></code >)</p @@ -272,9 +264,7 @@ ><table ><tr ><td class="src" - ><a href="#" - >Show</a - > x => <a id="v:BlubCtor" class="def" + >Show x => <a id="v:BlubCtor" class="def" >BlubCtor</a > x</td ><td class="doc empty" @@ -291,9 +281,7 @@ >Blub</a > :: () => <span class="keyword" >forall</span - > x. <a href="#" - >Show</a - > x => x -> <a href="#" + > x. Show x => x -> <a href="#" title="PatternSyns" >BlubType</a > <a href="#" class="selflink" >#</a @@ -301,7 +289,7 @@ ><div class="doc" ><p >Pattern synonym for <code - ><a href="#" + ><a href="#" title="PatternSyns" >Blub</a ></code > x</p @@ -311,9 +299,7 @@ ><p class="src" ><span class="keyword" >data</span - > (a :: <a href="#" - >*</a - >) <a id="t:-62--60-" class="def" + > (a :: *) <a id="t:-62--60-" class="def" >><</a > b <a href="#" class="selflink" >#</a @@ -321,7 +307,7 @@ ><div class="doc" ><p >Doc for (<code - ><a href="#" + ><a href="#" title="PatternSyns" >><</a ></code >)</p @@ -349,15 +335,15 @@ >E</a > :: <span class="keyword" >forall</span - > k a (b :: k). <a href="#" - >(><)</a - > k a b <a href="#" class="selflink" + > k a (b :: k). a <a href="#" title="PatternSyns" + >><</a + > b <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >Pattern for <code - ><a href="#" + ><a href="#" title="PatternSyns" >Empty</a ></code ></p @@ -369,9 +355,7 @@ >pattern</span > <a id="v:PatWithExplicitSig" class="def" >PatWithExplicitSig</a - > :: <a href="#" - >Eq</a - > somex => somex -> <a href="#" + > :: Eq somex => somex -> <a href="#" title="PatternSyns" >FooType</a > somex <a href="#" class="selflink" >#</a diff --git a/html-test/ref/PromotedTypes.html b/html-test/ref/PromotedTypes.html index 43736811..46a70845 100644 --- a/html-test/ref/PromotedTypes.html +++ b/html-test/ref/PromotedTypes.html @@ -64,7 +64,7 @@ ></tr ><tr ><td class="src" - >(<a href="#" + >(<a href="#" title="PromotedTypes" >RevList</a > a) <a id="v::-62-" class="def" >:></a @@ -81,11 +81,7 @@ >data</span > <a id="t:Pattern" class="def" >Pattern</a - > :: [<a href="#" - >*</a - >] -> <a href="#" - >*</a - > <span class="keyword" + > :: [*] -> * <span class="keyword" >where</span > <a href="#" class="selflink" >#</a @@ -98,7 +94,7 @@ ><td class="src" ><a id="v:Nil" class="def" >Nil</a - > :: <a href="#" + > :: <a href="#" title="PromotedTypes" >Pattern</a > '[]</td ><td class="doc empty" @@ -108,11 +104,9 @@ ><td class="src" ><a id="v:Cons" class="def" >Cons</a - > :: <a href="#" - >Maybe</a - > h -> <a href="#" + > :: Maybe h -> <a href="#" title="PromotedTypes" >Pattern</a - > t -> <a href="#" + > t -> <a href="#" title="PromotedTypes" >Pattern</a > (h ': t)</td ><td class="doc empty" @@ -127,13 +121,9 @@ >data</span > <a id="t:RevPattern" class="def" >RevPattern</a - > :: <a href="#" + > :: <a href="#" title="PromotedTypes" >RevList</a - > <a href="#" - >*</a - > -> <a href="#" - >*</a - > <span class="keyword" + > * -> * <span class="keyword" >where</span > <a href="#" class="selflink" >#</a @@ -146,9 +136,9 @@ ><td class="src" ><a id="v:RevNil" class="def" >RevNil</a - > :: <a href="#" + > :: <a href="#" title="PromotedTypes" >RevPattern</a - > <a href="#" + > <a href="#" title="PromotedTypes" >RNil</a ></td ><td class="doc empty" @@ -158,13 +148,11 @@ ><td class="src" ><a id="v:RevCons" class="def" >RevCons</a - > :: <a href="#" - >Maybe</a - > h -> <a href="#" + > :: Maybe h -> <a href="#" title="PromotedTypes" >RevPattern</a - > t -> <a href="#" + > t -> <a href="#" title="PromotedTypes" >RevPattern</a - > (t <a href="#" + > (t <a href="#" title="PromotedTypes" >:></a > h)</td ><td class="doc empty" @@ -179,13 +167,7 @@ >data</span > <a id="t:Tuple" class="def" >Tuple</a - > :: (<a href="#" - >*</a - >, <a href="#" - >*</a - >) -> <a href="#" - >*</a - > <span class="keyword" + > :: (*, *) -> * <span class="keyword" >where</span > <a href="#" class="selflink" >#</a @@ -198,7 +180,7 @@ ><td class="src" ><a id="v:Tuple" class="def" >Tuple</a - > :: a -> b -> <a href="#" + > :: a -> b -> <a href="#" title="PromotedTypes" >Tuple</a > '(a, b)</td ><td class="doc empty" diff --git a/html-test/ref/Properties.html b/html-test/ref/Properties.html index 15585cd9..9299486c 100644 --- a/html-test/ref/Properties.html +++ b/html-test/ref/Properties.html @@ -46,11 +46,7 @@ ><li class="src short" ><a href="#" >fib</a - > :: <a href="#" - >Integer</a - > -> <a href="#" - >Integer</a - ></li + > :: Integer -> Integer</li ></ul ></details ></div @@ -61,19 +57,13 @@ ><p class="src" ><a id="v:fib" class="def" >fib</a - > :: <a href="#" - >Integer</a - > -> <a href="#" - >Integer</a - > <a href="#" class="selflink" + > :: Integer -> Integer <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >Fibonacci number of given <code - ><a href="#" - >Integer</a - ></code + >Integer</code >.</p ><pre >fib n <= fib (n + 1)</pre diff --git a/html-test/ref/QuasiExpr.html b/html-test/ref/QuasiExpr.html index ccec6856..42b21f70 100644 --- a/html-test/ref/QuasiExpr.html +++ b/html-test/ref/QuasiExpr.html @@ -58,9 +58,7 @@ ><td class="src" ><a id="v:IntExpr" class="def" >IntExpr</a - > <a href="#" - >Integer</a - ></td + > Integer</td ><td class="doc empty" ></td ></tr @@ -68,9 +66,7 @@ ><td class="src" ><a id="v:AntiIntExpr" class="def" >AntiIntExpr</a - > <a href="#" - >String</a - ></td + > String</td ><td class="doc empty" ></td ></tr @@ -78,11 +74,11 @@ ><td class="src" ><a id="v:BinopExpr" class="def" >BinopExpr</a - > <a href="#" + > <a href="#" title="QuasiExpr" >BinOp</a - > <a href="#" + > <a href="#" title="QuasiExpr" >Expr</a - > <a href="#" + > <a href="#" title="QuasiExpr" >Expr</a ></td ><td class="doc empty" @@ -92,9 +88,7 @@ ><td class="src" ><a id="v:AntiExpr" class="def" >AntiExpr</a - > <a href="#" - >String</a - ></td + > String</td ><td class="doc empty" ></td ></tr @@ -110,9 +104,7 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:Expr:Show:1" ></span - > <a href="#" - >Show</a - > <a href="#" + > Show <a href="#" title="QuasiExpr" >Expr</a ></span > <a href="#" class="selflink" @@ -126,41 +118,31 @@ ><details id="i:id:Expr:Show:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >QuasiExpr</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >showsPrec</a - > :: <a href="#" - >Int</a - > -> <a href="#" + > :: Int -> <a href="#" title="QuasiExpr" >Expr</a - > -> <a href="#" - >ShowS</a - > <a href="#" class="selflink" - >#</a - ></p + > -> ShowS</p ><p class="src" ><a href="#" >show</a - > :: <a href="#" + > :: <a href="#" title="QuasiExpr" >Expr</a - > -> <a href="#" - >String</a - > <a href="#" class="selflink" - >#</a - ></p + > -> String</p ><p class="src" ><a href="#" >showList</a - > :: [<a href="#" + > :: [<a href="#" title="QuasiExpr" >Expr</a - >] -> <a href="#" - >ShowS</a - > <a href="#" class="selflink" - >#</a - ></p + >] -> ShowS</p ></div ></details ></td @@ -226,9 +208,7 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:BinOp:Show:1" ></span - > <a href="#" - >Show</a - > <a href="#" + > Show <a href="#" title="QuasiExpr" >BinOp</a ></span > <a href="#" class="selflink" @@ -242,41 +222,31 @@ ><details id="i:id:BinOp:Show:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >QuasiExpr</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >showsPrec</a - > :: <a href="#" - >Int</a - > -> <a href="#" + > :: Int -> <a href="#" title="QuasiExpr" >BinOp</a - > -> <a href="#" - >ShowS</a - > <a href="#" class="selflink" - >#</a - ></p + > -> ShowS</p ><p class="src" ><a href="#" >show</a - > :: <a href="#" + > :: <a href="#" title="QuasiExpr" >BinOp</a - > -> <a href="#" - >String</a - > <a href="#" class="selflink" - >#</a - ></p + > -> String</p ><p class="src" ><a href="#" >showList</a - > :: [<a href="#" + > :: [<a href="#" title="QuasiExpr" >BinOp</a - >] -> <a href="#" - >ShowS</a - > <a href="#" class="selflink" - >#</a - ></p + >] -> ShowS</p ></div ></details ></td @@ -289,11 +259,9 @@ ><p class="src" ><a id="v:eval" class="def" >eval</a - > :: <a href="#" + > :: <a href="#" title="QuasiExpr" >Expr</a - > -> <a href="#" - >Integer</a - > <a href="#" class="selflink" + > -> Integer <a href="#" class="selflink" >#</a ></p ></div @@ -309,9 +277,7 @@ ><p class="src" ><a id="v:parseExprExp" class="def" >parseExprExp</a - > :: <a href="#" - >String</a - > -> Q Exp <a href="#" class="selflink" + > :: String -> Q Exp <a href="#" class="selflink" >#</a ></p ></div diff --git a/html-test/ref/QuasiQuote.html b/html-test/ref/QuasiQuote.html index da2ffc4e..e9451d8a 100644 --- a/html-test/ref/QuasiQuote.html +++ b/html-test/ref/QuasiQuote.html @@ -45,9 +45,7 @@ ><p class="src" ><a id="v:val" class="def" >val</a - > :: <a href="#" - >Integer</a - > <a href="#" class="selflink" + > :: Integer <a href="#" class="selflink" >#</a ></p ></div diff --git a/html-test/ref/SpuriousSuperclassConstraints.html b/html-test/ref/SpuriousSuperclassConstraints.html index 53421ff5..00cea04a 100644 --- a/html-test/ref/SpuriousSuperclassConstraints.html +++ b/html-test/ref/SpuriousSuperclassConstraints.html @@ -73,11 +73,7 @@ Fix spurious superclass constraints bug.</pre >data</span > <a id="t:SomeType" class="def" >SomeType</a - > (f :: <a href="#" - >*</a - > -> <a href="#" - >*</a - >) a <a href="#" class="selflink" + > (f :: * -> *) a <a href="#" class="selflink" >#</a ></p ><div class="subs instances" @@ -90,9 +86,7 @@ Fix spurious superclass constraints bug.</pre ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:SomeType:Functor:1" ></span - > <a href="#" - >Functor</a - > (<a href="#" + > Functor (<a href="#" title="SpuriousSuperclassConstraints" >SomeType</a > f)</span > <a href="#" class="selflink" @@ -106,29 +100,29 @@ Fix spurious superclass constraints bug.</pre ><details id="i:id:SomeType:Functor:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >SpuriousSuperclassConstraints</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >fmap</a - > :: (a -> b) -> <a href="#" + > :: (a -> b) -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f a -> <a href="#" + > f a -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f b <a href="#" class="selflink" - >#</a - ></p + > f b</p ><p class="src" ><a href="#" >(<$)</a - > :: a -> <a href="#" + > :: a -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f b -> <a href="#" + > f b -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f a <a href="#" class="selflink" - >#</a - ></p + > f a</p ></div ></details ></td @@ -138,11 +132,7 @@ Fix spurious superclass constraints bug.</pre ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:SomeType:Applicative:2" ></span - > <a href="#" - >Applicative</a - > f => <a href="#" - >Applicative</a - > (<a href="#" + > Applicative f => Applicative (<a href="#" title="SpuriousSuperclassConstraints" >SomeType</a > f)</span > <a href="#" class="selflink" @@ -156,65 +146,59 @@ Fix spurious superclass constraints bug.</pre ><details id="i:id:SomeType:Applicative:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >SpuriousSuperclassConstraints</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >pure</a - > :: a -> <a href="#" + > :: a -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f a <a href="#" class="selflink" - >#</a - ></p + > f a</p ><p class="src" ><a href="#" >(<*>)</a - > :: <a href="#" + > :: <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f (a -> b) -> <a href="#" + > f (a -> b) -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f a -> <a href="#" + > f a -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f b <a href="#" class="selflink" - >#</a - ></p + > f b</p ><p class="src" ><a href="#" >liftA2</a - > :: (a -> b -> c) -> <a href="#" + > :: (a -> b -> c) -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f a -> <a href="#" + > f a -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f b -> <a href="#" + > f b -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f c <a href="#" class="selflink" - >#</a - ></p + > f c</p ><p class="src" ><a href="#" >(*>)</a - > :: <a href="#" + > :: <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f a -> <a href="#" + > f a -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f b -> <a href="#" + > f b -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f b <a href="#" class="selflink" - >#</a - ></p + > f b</p ><p class="src" ><a href="#" >(<*)</a - > :: <a href="#" + > :: <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f a -> <a href="#" + > f a -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f b -> <a href="#" + > f b -> <a href="#" title="SpuriousSuperclassConstraints" >SomeType</a - > f a <a href="#" class="selflink" - >#</a - ></p + > f a</p ></div ></details ></td diff --git a/html-test/ref/Table.html b/html-test/ref/Table.html new file mode 100644 index 00000000..deaf6b1c --- /dev/null +++ b/html-test/ref/Table.html @@ -0,0 +1,238 @@ +<html xmlns="http://www.w3.org/1999/xhtml" +><head + ><meta http-equiv="Content-Type" content="text/html; charset=UTF-8" + /><title + >Table</title + ><link href="#" rel="stylesheet" type="text/css" title="Ocean" + /><link rel="stylesheet" type="text/css" href="#" + /><script src="haddock-bundle.min.js" async="async" type="text/javascript" + ></script + ><script src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.0/MathJax.js?config=TeX-AMS-MML_HTMLorMML" type="text/javascript" + ></script + ></head + ><body + ><div id="package-header" + ><ul class="links" id="page-menu" + ><li + ><a href="#" + >Contents</a + ></li + ><li + ><a href="#" + >Index</a + ></li + ></ul + ><p class="caption empty" + ></p + ></div + ><div id="content" + ><div id="module-header" + ><table class="info" + ><tr + ><th + >Safe Haskell</th + ><td + >Safe</td + ></tr + ></table + ><p class="caption" + >Table</p + ></div + ><div id="description" + ><p class="caption" + >Description</p + ><div class="doc" + ><p + >This tests the table markup</p + ></div + ></div + ><div id="synopsis" + ><details id="syn" + ><summary + >Synopsis</summary + ><ul class="details-toggle" data-details-id="syn" + ><li class="src short" + ><a href="#" + >tableWithHeader</a + > :: a -> a</li + ><li class="src short" + ><a href="#" + >tableWithoutHeader</a + > :: a -> a</li + ><li class="src short" + ><a href="#" + >fancyTable</a + > :: a -> a</li + ></ul + ></details + ></div + ><div id="interface" + ><h1 + >Documentation</h1 + ><div class="top" + ><p class="src" + ><a id="v:tableWithHeader" class="def" + >tableWithHeader</a + > :: a -> a <a href="#" class="selflink" + >#</a + ></p + ><div class="doc" + ><p + >Table with header.</p + ><table + ><thead + ><tr + ><th + > code </th + ><th + > message </th + ><th + > description </th + ></tr + ></thead + ><tbody + ><tr + ><td + > 200 </td + ><td + > <code + >OK</code + > </td + ><td + > operation successful </td + ></tr + ><tr + ><td + > 204 </td + ><td + > <code + >No Content</code + > </td + ><td + > operation successful, no body returned </td + ></tr + ></tbody + ></table + ></div + ></div + ><div class="top" + ><p class="src" + ><a id="v:tableWithoutHeader" class="def" + >tableWithoutHeader</a + > :: a -> a <a href="#" class="selflink" + >#</a + ></p + ><div class="doc" + ><p + >Table without header.</p + ><table + ><tbody + ><tr + ><td + > 200 </td + ><td + > <code + >OK</code + > </td + ><td + > operation successful </td + ></tr + ><tr + ><td + > 204 </td + ><td + > <code + >No Content</code + > </td + ><td + > operation successful, no body returned </td + ></tr + ><tr + ><td + > 404 </td + ><td + > <code + >Not Found</code + > </td + ><td + > resource not found </td + ></tr + ></tbody + ></table + ></div + ></div + ><div class="top" + ><p class="src" + ><a id="v:fancyTable" class="def" + >fancyTable</a + > :: a -> a <a href="#" class="selflink" + >#</a + ></p + ><div class="doc" + ><p + >Fancy table.</p + ><table + ><thead + ><tr + ><th + > Header row, column 1 + (header rows optional) </th + ><th + > Header 2 + </th + ><th + > Header 3 + </th + ><th + > Header 4 + </th + ></tr + ></thead + ><tbody + ><tr + ><td + > body row 1, column 1 </td + ><td + > column 2 </td + ><td + > column 3 </td + ><td + > column 4 </td + ></tr + ><tr + ><td + > <code + ><a href="#" title="Table" + >tableWithHeader</a + ></code + > </td + ><td colspan="3" + > Cells may span columns. </td + ></tr + ><tr + ><td + > body row 3 </td + ><td rowspan="2" + > Cells may + span rows. + </td + ><td colspan="2" rowspan="2" + > \[ + f(n) = \sum_{i=1} + \] </td + ></tr + ><tr + ><td + > body row 4 </td + ></tr + ></tbody + ></table + ></div + ></div + ></div + ></div + ><div id="footer" + ></div + ></body + ></html +>
\ No newline at end of file diff --git a/html-test/ref/Test.html b/html-test/ref/Test.html index 4bcd2508..d4c2417c 100644 --- a/html-test/ref/Test.html +++ b/html-test/ref/Test.html @@ -133,19 +133,19 @@ ><p >This module illustrates & tests most of the features of Haddock. Testing references from the description: <code - ><a href="#" + ><a href="#" title="Test" >T</a ></code >, <code - ><a href="#" + ><a href="#" title="Test" >f</a ></code >, <code - ><a href="#" + ><a href="#" title="Test" >g</a ></code >, <code - ><a href="#" + ><a href="#" title="Visible" >visible</a ></code >.</p @@ -165,25 +165,15 @@ ><li >= <a href="#" >A</a - > <a href="#" - >Int</a - > (<a href="#" - >Maybe</a - > <a href="#" - >Float</a - >)</li + > Int (Maybe Float)</li ><li >| <a href="#" >B</a - > (<a href="#" + > (<a href="#" title="Test" >T</a - > a b, <a href="#" + > a b, <a href="#" title="Test" >T</a - > <a href="#" - >Int</a - > <a href="#" - >Float</a - >)</li + > Int Float)</li ></ul ></li ><li class="src short" @@ -357,9 +347,7 @@ ><li ><a href="#" >p</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li ><a href="#" >q</a @@ -371,9 +359,7 @@ >r</a >, <a href="#" >s</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul > }</li ><li @@ -383,25 +369,13 @@ ><li ><a href="#" >t</a - > :: T1 -> <a href="#" + > :: T1 -> <a href="#" title="Test" >T2</a - > <a href="#" - >Int</a - > <a href="#" - >Int</a - > -> <a href="#" + > Int Int -> <a href="#" title="Test" >T3</a - > <a href="#" - >Bool</a - > <a href="#" - >Bool</a - > -> <a href="#" + > Bool Bool -> <a href="#" title="Test" >T4</a - > <a href="#" - >Float</a - > <a href="#" - >Float</a - > -> <a href="#" + > Float Float -> <a href="#" title="Test" >T5</a > () ()</li ><li @@ -409,9 +383,7 @@ >u</a >, <a href="#" >v</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul > }</li ></ul @@ -427,34 +399,56 @@ ><li ><a href="#" >s1</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li ><a href="#" >s2</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li ><a href="#" >s3</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul >}</li ><li class="src short" + ><a href="#" + >p</a + > :: <a href="#" title="Test" + >R</a + > -> Int</li + ><li class="src short" + ><a href="#" + >q</a + > :: <a href="#" title="Test" + >R</a + > -> <span class="keyword" + >forall</span + > a. a -> a</li + ><li class="src short" + ><a href="#" + >u</a + > :: <a href="#" title="Test" + >R</a + > -> Int</li + ><li class="src short" ><span class="keyword" >class</span - > <a href="#" + > <a href="#" title="Test" >D</a > a => <a href="#" >C</a > a <span class="keyword" >where</span ><ul class="subs" - ></ul + ><li + ><a href="#" + >a</a + > :: IO a</li + ><li + ><a href="#" + >b</a + > :: [a]</li + ></ul ></li ><li class="src short" ><span class="keyword" @@ -464,7 +458,17 @@ > a <span class="keyword" >where</span ><ul class="subs" - ></ul + ><li + ><a href="#" + >d</a + > :: <a href="#" title="Test" + >T</a + > a b</li + ><li + ><a href="#" + >e</a + > :: (a, a)</li + ></ul ></li ><li class="src short" ><span class="keyword" @@ -480,40 +484,32 @@ > a <span class="keyword" >where</span ><ul class="subs" - ></ul + ><li + ><a href="#" + >ff</a + > :: a</li + ></ul ></li ><li class="src short" ><a href="#" >a</a - > :: <a href="#" + > :: <a href="#" title="Test" >C</a - > a => <a href="#" - >IO</a - > a</li + > a => IO a</li ><li class="src short" ><a href="#" >f</a - > :: <a href="#" + > :: <a href="#" title="Test" >C</a - > a => a -> <a href="#" - >Int</a - ></li + > a => a -> Int</li ><li class="src short" ><a href="#" >g</a - > :: <a href="#" - >Int</a - > -> <a href="#" - >IO</a - > CInt</li + > :: Int -> IO CInt</li ><li class="src short" ><a href="#" >hidden</a - > :: <a href="#" - >Int</a - > -> <a href="#" - >Int</a - ></li + > :: Int -> Int</li ><li class="src short" >module <a href="#" >Visible</a @@ -525,7 +521,7 @@ >Ex</a > a<ul class="subs" ><li - >= <a href="#" + >= <a href="#" title="Test" >C</a > b => <a href="#" >Ex1</a @@ -535,7 +531,7 @@ >Ex2</a > b</li ><li - >| <a href="#" + >| <a href="#" title="Test" >C</a > a => <a href="#" >Ex3</a @@ -551,77 +547,41 @@ ><li class="src short" ><a href="#" >k</a - > :: <a href="#" + > :: <a href="#" title="Test" >T</a - > () () -> <a href="#" + > () () -> <a href="#" title="Test" >T2</a - > <a href="#" - >Int</a - > <a href="#" - >Int</a - > -> (<a href="#" + > Int Int -> (<a href="#" title="Test" >T3</a - > <a href="#" - >Bool</a - > <a href="#" - >Bool</a - > -> <a href="#" + > Bool Bool -> <a href="#" title="Test" >T4</a - > <a href="#" - >Float</a - > <a href="#" - >Float</a - >) -> <a href="#" + > Float Float) -> <a href="#" title="Test" >T5</a - > () () -> <a href="#" - >IO</a - > ()</li + > () () -> IO ()</li ><li class="src short" ><a href="#" >l</a - > :: (<a href="#" - >Int</a - >, <a href="#" - >Int</a - >, <a href="#" - >Float</a - >) -> <a href="#" - >Int</a - ></li + > :: (Int, Int, Float) -> Int</li ><li class="src short" ><a href="#" >m</a - > :: <a href="#" + > :: <a href="#" title="Test" >R</a - > -> <a href="#" + > -> <a href="#" title="Test" >N1</a - > () -> <a href="#" - >IO</a - > <a href="#" - >Int</a - ></li + > () -> IO Int</li ><li class="src short" ><a href="#" >o</a - > :: <a href="#" - >Float</a - > -> <a href="#" - >IO</a - > <a href="#" - >Float</a - ></li + > :: Float -> IO Float</li ><li class="src short" ><a href="#" >f'</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >withType</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ><li class="src short" ><a href="#" >withoutType</a @@ -630,10 +590,14 @@ ></details ></div ><div id="interface" - ><h1 id="g:1" - >Type declarations</h1 - ><h2 id="g:2" - >Data types</h2 + ><a href="#" id="g:1" + ><h1 + >Type declarations</h1 + ></a + ><a href="#" id="g:2" + ><h2 + >Data types</h2 + ></a ><div class="top" ><p class="src" ><span class="keyword" @@ -658,17 +622,11 @@ ><td class="src" ><a id="v:A" class="def" >A</a - > <a href="#" - >Int</a - > (<a href="#" - >Maybe</a - > <a href="#" - >Float</a - >)</td + > Int (Maybe Float)</td ><td class="doc" ><p >This comment describes the <code - ><a href="#" + ><a href="#" title="Test" >A</a ></code > constructor</p @@ -678,19 +636,15 @@ ><td class="src" ><a id="v:B" class="def" >B</a - > (<a href="#" + > (<a href="#" title="Test" >T</a - > a b, <a href="#" + > a b, <a href="#" title="Test" >T</a - > <a href="#" - >Int</a - > <a href="#" - >Float</a - >)</td + > Int Float)</td ><td class="doc" ><p >This comment describes the <code - ><a href="#" + ><a href="#" title="Test" >B</a ></code > constructor</p @@ -802,7 +756,7 @@ ><td class="doc" ><p >documents <code - ><a href="#" + ><a href="#" title="Test" >A3</a ></code ></p @@ -816,7 +770,7 @@ ><td class="doc" ><p >documents <code - ><a href="#" + ><a href="#" title="Test" >B3</a ></code ></p @@ -850,7 +804,7 @@ ><td class="doc" ><p >This is the doc for <code - ><a href="#" + ><a href="#" title="Test" >A4</a ></code ></p @@ -864,7 +818,7 @@ ><td class="doc" ><p >This is the doc for <code - ><a href="#" + ><a href="#" title="Test" >B4</a ></code ></p @@ -878,7 +832,7 @@ ><td class="doc" ><p >This is the doc for <code - ><a href="#" + ><a href="#" title="Test" >C4</a ></code ></p @@ -1000,7 +954,7 @@ ><div class="doc" ><p >this is the <code - ><a href="#" + ><a href="#" title="Test" >n3</a ></code > field</p @@ -1141,7 +1095,7 @@ ><td class="doc" ><p >The <code - ><a href="#" + ><a href="#" title="Test" >N7</a ></code > constructor</p @@ -1168,8 +1122,10 @@ ></table ></div ></div - ><h2 id="g:3" - >Records</h2 + ><a href="#" id="g:3" + ><h2 + >Records</h2 + ></a ><div class="top" ><p class="src" ><span class="keyword" @@ -1182,24 +1138,24 @@ ><div class="doc" ><p >This is the documentation for the <code - ><a href="#" + ><a href="#" title="Test" >R</a ></code > record, which has four fields, <code - ><a href="#" + ><a href="#" title="Test" >p</a ></code >, <code - ><a href="#" + ><a href="#" title="Test" >q</a ></code >, <code - ><a href="#" + ><a href="#" title="Test" >r</a ></code >, and <code - ><a href="#" + ><a href="#" title="Test" >s</a ></code >.</p @@ -1216,7 +1172,7 @@ ><td class="doc" ><p >This is the <code - ><a href="#" + ><a href="#" title="Test" >C1</a ></code > record constructor, with the following fields:</p @@ -1232,13 +1188,11 @@ ><dfn class="src" ><a id="v:p" class="def" >p</a - > :: <a href="#" - >Int</a - ></dfn + > :: Int</dfn ><div class="doc" ><p >This comment applies to the <code - ><a href="#" + ><a href="#" title="Test" >p</a ></code > field</p @@ -1254,7 +1208,7 @@ ><div class="doc" ><p >This comment applies to the <code - ><a href="#" + ><a href="#" title="Test" >q</a ></code > field</p @@ -1266,17 +1220,15 @@ >r</a >, <a id="v:s" class="def" >s</a - > :: <a href="#" - >Int</a - ></dfn + > :: Int</dfn ><div class="doc" ><p >This comment applies to both <code - ><a href="#" + ><a href="#" title="Test" >r</a ></code > and <code - ><a href="#" + ><a href="#" title="Test" >s</a ></code ></p @@ -1294,7 +1246,7 @@ ><td class="doc" ><p >This is the <code - ><a href="#" + ><a href="#" title="Test" >C2</a ></code > record constructor, also with some fields:</p @@ -1310,25 +1262,13 @@ ><dfn class="src" ><a id="v:t" class="def" >t</a - > :: T1 -> <a href="#" + > :: T1 -> <a href="#" title="Test" >T2</a - > <a href="#" - >Int</a - > <a href="#" - >Int</a - > -> <a href="#" + > Int Int -> <a href="#" title="Test" >T3</a - > <a href="#" - >Bool</a - > <a href="#" - >Bool</a - > -> <a href="#" + > Bool Bool -> <a href="#" title="Test" >T4</a - > <a href="#" - >Float</a - > <a href="#" - >Float</a - > -> <a href="#" + > Float Float -> <a href="#" title="Test" >T5</a > () ()</dfn ><div class="doc empty" @@ -1340,9 +1280,7 @@ >u</a >, <a id="v:v" class="def" >v</a - > :: <a href="#" - >Int</a - ></dfn + > :: Int</dfn ><div class="doc empty" ></div ></li @@ -1378,7 +1316,7 @@ ><td class="doc" ><p >This is the <code - ><a href="#" + ><a href="#" title="Test" >C3</a ></code > record constructor</p @@ -1394,13 +1332,11 @@ ><dfn class="src" ><a id="v:s1" class="def" >s1</a - > :: <a href="#" - >Int</a - ></dfn + > :: Int</dfn ><div class="doc" ><p >The <code - ><a href="#" + ><a href="#" title="Test" >s1</a ></code > record selector</p @@ -1410,13 +1346,11 @@ ><dfn class="src" ><a id="v:s2" class="def" >s2</a - > :: <a href="#" - >Int</a - ></dfn + > :: Int</dfn ><div class="doc" ><p >The <code - ><a href="#" + ><a href="#" title="Test" >s2</a ></code > record selector</p @@ -1426,13 +1360,11 @@ ><dfn class="src" ><a id="v:s3" class="def" >s3</a - > :: <a href="#" - >Int</a - ></dfn + > :: Int</dfn ><div class="doc" ><p >The <code - ><a href="#" + ><a href="#" title="Test" >s3</a ></code > record selector</p @@ -1449,13 +1381,63 @@ ><p >test that we can export record selectors on their own:</p ></div - ><h1 id="g:4" - >Class declarations</h1 + ><div class="top" + ><p class="src" + ><a id="v:p" class="def" + >p</a + > :: <a href="#" title="Test" + >R</a + > -> Int <a href="#" class="selflink" + >#</a + ></p + ><div class="doc" + ><p + >This comment applies to the <code + ><a href="#" title="Test" + >p</a + ></code + > field</p + ></div + ></div + ><div class="top" + ><p class="src" + ><a id="v:q" class="def" + >q</a + > :: <a href="#" title="Test" + >R</a + > -> <span class="keyword" + >forall</span + > a. a -> a <a href="#" class="selflink" + >#</a + ></p + ><div class="doc" + ><p + >This comment applies to the <code + ><a href="#" title="Test" + >q</a + ></code + > field</p + ></div + ></div + ><div class="top" + ><p class="src" + ><a id="v:u" class="def" + >u</a + > :: <a href="#" title="Test" + >R</a + > -> Int <a href="#" class="selflink" + >#</a + ></p + ></div + ><a href="#" id="g:4" + ><h1 + >Class declarations</h1 + ></a ><div class="top" ><p class="src" ><span class="keyword" >class</span - > <a href="#" + > <a href="#" title="Test" >D</a > a => <a id="t:C" class="def" >C</a @@ -1469,36 +1451,24 @@ >This comment applies to the <em >previous</em > declaration (the <code - ><a href="#" + ><a href="#" title="Test" >C</a ></code > class)</p ></div - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >a</a - >, <a href="#" - >b</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a id="v:a" class="def" >a</a - > :: <a href="#" - >IO</a - > a <a href="#" class="selflink" + > :: IO a <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >this is a description of the <code - ><a href="#" + ><a href="#" title="Test" >a</a ></code > method</p @@ -1512,7 +1482,7 @@ ><div class="doc" ><p >this is a description of the <code - ><a href="#" + ><a href="#" title="Test" >b</a ></code > method</p @@ -1534,23 +1504,13 @@ ><p >This is a class declaration with no separate docs for the methods</p ></div - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >d</a - >, <a href="#" - >e</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a id="v:d" class="def" >d</a - > :: <a href="#" + > :: <a href="#" title="Test" >T</a > a b <a href="#" class="selflink" >#</a @@ -1572,11 +1532,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:D:D:1" ></span - > <a href="#" + > <a href="#" title="Test" >D</a - > <a href="#" - >Float</a - ></span + > Float</span > <a href="#" class="selflink" >#</a ></td @@ -1588,27 +1546,25 @@ ><details id="i:ic:D:D:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Test</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >d</a - > :: <a href="#" + > :: <a href="#" title="Test" >T</a - > <a href="#" - >Float</a - > b <a href="#" class="selflink" + > Float b <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >e</a - > :: (<a href="#" - >Float</a - >, <a href="#" - >Float</a - >) <a href="#" class="selflink" + > :: (Float, Float) <a href="#" class="selflink" >#</a ></p ></div @@ -1620,11 +1576,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:D:D:2" ></span - > <a href="#" + > <a href="#" title="Test" >D</a - > <a href="#" - >Int</a - ></span + > Int</span > <a href="#" class="selflink" >#</a ></td @@ -1636,27 +1590,25 @@ ><details id="i:ic:D:D:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs methods" + ><p + >Defined in <a href="#" + >Test</a + ></p + > <div class="subs methods" ><p class="caption" >Methods</p ><p class="src" ><a href="#" >d</a - > :: <a href="#" + > :: <a href="#" title="Test" >T</a - > <a href="#" - >Int</a - > b <a href="#" class="selflink" + > Int b <a href="#" class="selflink" >#</a ></p ><p class="src" ><a href="#" >e</a - > :: (<a href="#" - >Int</a - >, <a href="#" - >Int</a - >) <a href="#" class="selflink" + > :: (Int, Int) <a href="#" class="selflink" >#</a ></p ></div @@ -1698,14 +1650,6 @@ > <a href="#" class="selflink" >#</a ></p - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >ff</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p @@ -1725,40 +1669,38 @@ ><p class="src" ><a id="v:a" class="def" >a</a - > :: <a href="#" + > :: <a href="#" title="Test" >C</a - > a => <a href="#" - >IO</a - > a <a href="#" class="selflink" + > a => IO a <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >this is a description of the <code - ><a href="#" + ><a href="#" title="Test" >a</a ></code > method</p ></div ></div - ><h1 id="g:5" - >Function types</h1 + ><a href="#" id="g:5" + ><h1 + >Function types</h1 + ></a ><div class="top" ><p class="src" ><a id="v:f" class="def" >f</a - > :: <a href="#" + > :: <a href="#" title="Test" >C</a - > a => a -> <a href="#" - >Int</a - > <a href="#" class="selflink" + > a => a -> Int <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >In a comment string we can refer to identifiers in scope with single quotes like this: <code - ><a href="#" + ><a href="#" title="Test" >T</a ></code >, and we can refer to modules by @@ -1791,7 +1733,7 @@ using double quotes: <a href="#" ></dl ><pre > This is a block of code, which can include other markup: <code - ><a href="#" + ><a href="#" title="Test" >R</a ></code > @@ -1811,11 +1753,7 @@ using double quotes: <a href="#" ><p class="src" ><a id="v:g" class="def" >g</a - > :: <a href="#" - >Int</a - > -> <a href="#" - >IO</a - > CInt <a href="#" class="selflink" + > :: Int -> IO CInt <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -1823,8 +1761,10 @@ using double quotes: <a href="#" >we can export foreign declarations too</p ></div ></div - ><h1 id="g:6" - >Auxiliary stuff</h1 + ><a href="#" id="g:6" + ><h1 + >Auxiliary stuff</h1 + ></a ><div class="doc" ><p >This is some documentation that is attached to a name ($aux1) @@ -1916,22 +1856,22 @@ test2 each line must begin with > (which isn't significant unless it is at the beginning of the line).</pre ></div - ><h1 id="g:7" - >A hidden module</h1 + ><a href="#" id="g:7" + ><h1 + >A hidden module</h1 + ></a ><div class="top" ><p class="src" ><a id="v:hidden" class="def" >hidden</a - > :: <a href="#" - >Int</a - > -> <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int -> Int <a href="#" class="selflink" >#</a ></p ></div - ><h1 id="g:8" - >A visible module</h1 + ><a href="#" id="g:8" + ><h1 + >A visible module</h1 + ></a ><div class="top" ><p class="src" >module <a href="#" @@ -1942,8 +1882,10 @@ is at the beginning of the line).</pre ><p >nested-style doc comments </p ></div - ><h1 id="g:9" - >Existential / Universal types</h1 + ><a href="#" id="g:9" + ><h1 + >Existential / Universal types</h1 + ></a ><div class="top" ><p class="src" ><span class="keyword" @@ -1963,7 +1905,7 @@ is at the beginning of the line).</pre ><table ><tr ><td class="src" - ><a href="#" + ><a href="#" title="Test" >C</a > b => <a id="v:Ex1" class="def" >Ex1</a @@ -1981,7 +1923,7 @@ is at the beginning of the line).</pre ></tr ><tr ><td class="src" - ><a href="#" + ><a href="#" title="Test" >C</a > a => <a id="v:Ex3" class="def" >Ex3</a @@ -2002,8 +1944,10 @@ is at the beginning of the line).</pre ></table ></div ></div - ><h1 id="g:10" - >Type signatures with argument docs</h1 + ><a href="#" id="g:10" + ><h1 + >Type signatures with argument docs</h1 + ></a ><div class="top" ><p class="src" ><a id="v:k" class="def" @@ -2017,13 +1961,13 @@ is at the beginning of the line).</pre ><table ><tr ><td class="src" - >:: <a href="#" + >:: <a href="#" title="Test" >T</a > () ()</td ><td class="doc" ><p >This argument has type <code - ><a href="#" + ><a href="#" title="Test" >T</a ></code ></p @@ -2031,13 +1975,9 @@ is at the beginning of the line).</pre ></tr ><tr ><td class="src" - >-> <a href="#" + >-> <a href="#" title="Test" >T2</a - > <a href="#" - >Int</a - > <a href="#" - >Int</a - ></td + > Int Int</td ><td class="doc" ><p >This argument has type 'T2 Int Int'</p @@ -2045,19 +1985,11 @@ is at the beginning of the line).</pre ></tr ><tr ><td class="src" - >-> (<a href="#" + >-> (<a href="#" title="Test" >T3</a - > <a href="#" - >Bool</a - > <a href="#" - >Bool</a - > -> <a href="#" + > Bool Bool -> <a href="#" title="Test" >T4</a - > <a href="#" - >Float</a - > <a href="#" - >Float</a - >)</td + > Float Float)</td ><td class="doc" ><p >This argument has type <code @@ -2067,7 +1999,7 @@ is at the beginning of the line).</pre ></tr ><tr ><td class="src" - >-> <a href="#" + >-> <a href="#" title="Test" >T5</a > () ()</td ><td class="doc" @@ -2079,9 +2011,7 @@ is at the beginning of the line).</pre ></tr ><tr ><td class="src" - >-> <a href="#" - >IO</a - > ()</td + >-> IO ()</td ><td class="doc" ><p >This is the result type</p @@ -2107,13 +2037,7 @@ is at the beginning of the line).</pre ><table ><tr ><td class="src" - >:: (<a href="#" - >Int</a - >, <a href="#" - >Int</a - >, <a href="#" - >Float</a - >)</td + >:: (Int, Int, Float)</td ><td class="doc" ><p >takes a triple</p @@ -2121,15 +2045,11 @@ is at the beginning of the line).</pre ></tr ><tr ><td class="src" - >-> <a href="#" - >Int</a - ></td + >-> Int</td ><td class="doc" ><p >returns an <code - ><a href="#" - >Int</a - ></code + >Int</code ></p ></td ></tr @@ -2149,7 +2069,7 @@ is at the beginning of the line).</pre ><table ><tr ><td class="src" - >:: <a href="#" + >:: <a href="#" title="Test" >R</a ></td ><td class="doc empty" @@ -2157,7 +2077,7 @@ is at the beginning of the line).</pre ></tr ><tr ><td class="src" - >-> <a href="#" + >-> <a href="#" title="Test" >N1</a > ()</td ><td class="doc" @@ -2167,11 +2087,7 @@ is at the beginning of the line).</pre ></tr ><tr ><td class="src" - >-> <a href="#" - >IO</a - > <a href="#" - >Int</a - ></td + >-> IO Int</td ><td class="doc" ><p >and the return value</p @@ -2197,9 +2113,7 @@ is at the beginning of the line).</pre ><table ><tr ><td class="src" - >:: <a href="#" - >Float</a - ></td + >:: Float</td ><td class="doc" ><p >The input float</p @@ -2207,11 +2121,7 @@ is at the beginning of the line).</pre ></tr ><tr ><td class="src" - >-> <a href="#" - >IO</a - > <a href="#" - >Float</a - ></td + >-> IO Float</td ><td class="doc" ><p >The output float</p @@ -2224,10 +2134,14 @@ is at the beginning of the line).</pre >A foreign import with argument docs</p ></div ></div - ><h1 id="g:11" - >A section</h1 - ><h2 id="g:12" - >A subsection</h2 + ><a href="#" id="g:11" + ><h1 + >A section</h1 + ></a + ><a href="#" id="g:12" + ><h2 + >A subsection</h2 + ></a ><div class="doc" ><pre >a literal line</pre @@ -2240,15 +2154,13 @@ is at the beginning of the line).</pre ><p class="src" ><a id="v:f-39-" class="def" >f'</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >a function with a prime can be referred to as <code - ><a href="#" + ><a href="#" title="Test" >f'</a ></code > @@ -2259,9 +2171,7 @@ is at the beginning of the line).</pre ><p class="src" ><a id="v:withType" class="def" >withType</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/Threaded.html b/html-test/ref/Threaded.html index 836a4db2..8728d4cd 100644 --- a/html-test/ref/Threaded.html +++ b/html-test/ref/Threaded.html @@ -56,9 +56,7 @@ ><li class="src short" ><a href="#" >f</a - > :: <a href="#" - >Integer</a - ></li + > :: Integer</li ></ul ></details ></div @@ -69,9 +67,7 @@ ><p class="src" ><a id="v:f" class="def" >f</a - > :: <a href="#" - >Integer</a - > <a href="#" class="selflink" + > :: Integer <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/Ticket112.html b/html-test/ref/Ticket112.html index ccd39ff0..a2c4ca1b 100644 --- a/html-test/ref/Ticket112.html +++ b/html-test/ref/Ticket112.html @@ -63,9 +63,7 @@ ><div class="doc" ><p >...given a raw <code - ><a href="#" - >Addr#</a - ></code + >Addr#</code > to the string, and the length of the string.</p ></div ></div diff --git a/html-test/ref/Ticket61.html b/html-test/ref/Ticket61.html index 2581584a..9cab5271 100644 --- a/html-test/ref/Ticket61.html +++ b/html-test/ref/Ticket61.html @@ -52,14 +52,6 @@ > <a href="#" class="selflink" >#</a ></p - ><div class="subs minimal" - ><p class="caption" - >Minimal complete definition</p - ><p class="src" - ><a href="#" - >f</a - ></p - ></div ><div class="subs methods" ><p class="caption" >Methods</p diff --git a/html-test/ref/Ticket75.html b/html-test/ref/Ticket75.html index 488913b1..683a7184 100644 --- a/html-test/ref/Ticket75.html +++ b/html-test/ref/Ticket75.html @@ -54,9 +54,7 @@ ><li class="src short" ><a href="#" >f</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div @@ -91,15 +89,13 @@ ><p class="src" ><a id="v:f" class="def" >f</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >A reference to <code - ><a href="#" + ><a href="#" title="Ticket75" >:-</a ></code ></p diff --git a/html-test/ref/TitledPicture.html b/html-test/ref/TitledPicture.html index 966c2a34..1e6f50e0 100644 --- a/html-test/ref/TitledPicture.html +++ b/html-test/ref/TitledPicture.html @@ -46,15 +46,11 @@ ><li class="src short" ><a href="#" >foo</a - > :: <a href="#" - >Integer</a - ></li + > :: Integer</li ><li class="src short" ><a href="#" >bar</a - > :: <a href="#" - >Integer</a - ></li + > :: Integer</li ></ul ></details ></div @@ -65,15 +61,13 @@ ><p class="src" ><a id="v:foo" class="def" >foo</a - > :: <a href="#" - >Integer</a - > <a href="#" class="selflink" + > :: Integer <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >Picture for <code - ><a href="#" + ><a href="#" title="TitledPicture" >foo</a ></code > without a title <img src="bar" @@ -84,15 +78,13 @@ ><p class="src" ><a id="v:bar" class="def" >bar</a - > :: <a href="#" - >Integer</a - > <a href="#" class="selflink" + > :: Integer <a href="#" class="selflink" >#</a ></p ><div class="doc" ><p >Picture for <code - ><a href="#" + ><a href="#" title="TitledPicture" >bar</a ></code > with title <img src="un∣∁∘" title="δ∈" diff --git a/html-test/ref/TypeFamilies.html b/html-test/ref/TypeFamilies.html index dcb5a92a..2195a05a 100644 --- a/html-test/ref/TypeFamilies.html +++ b/html-test/ref/TypeFamilies.html @@ -110,9 +110,7 @@ >data family</span > <a href="#" >Bat</a - > (a :: k) :: <a href="#" - >*</a - ></li + > (a :: k) :: *</li ><li class="src short" ><span class="keyword" >class</span @@ -126,17 +124,13 @@ >data</span > <a href="#" >AssocD</a - > a :: <a href="#" - >*</a - ></li + > a :: *</li ><li ><span class="keyword" >type</span > <a href="#" >AssocT</a - > a :: <a href="#" - >*</a - ></li + > a :: *</li ></ul ></li ><li class="src short" @@ -224,13 +218,11 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:X:-62--60-:1" ></span - > <a href="#" - >(><)</a - > <a href="#" - >X</a - > <a href="#" + > <a href="#" title="TypeFamilies" >XX</a - > <a href="#" + > <a href="#" title="TypeFamilies" + >><</a + > <a href="#" title="TypeFamilies" >XXX</a ></span > <a href="#" class="selflink" @@ -244,6 +236,10 @@ ><details id="i:id:X:-62--60-:1" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p ></details ></td ></tr @@ -252,11 +248,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:X:Assoc:2" ></span - > <a href="#" + > <a href="#" title="TypeFamilies" >Assoc</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -272,35 +266,31 @@ ><details id="i:id:X:Assoc:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs associated-types" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="subs associated-types" ><p class="caption" >Associated Types</p ><p class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocD</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > (a :: <a href="#" - >X</a - >) :: <a href="#" - >*</a - > <a href="#" class="selflink" + > :: * <a href="#" class="selflink" >#</a ></p ><p class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocT</a - > <a href="#" - >X</a - > (a :: <a href="#" + > <a href="#" title="TypeFamilies" >X</a - >) :: <a href="#" - >*</a - > <a href="#" class="selflink" + > :: * <a href="#" class="selflink" >#</a ></p ></div @@ -312,11 +302,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:X:Test:3" ></span - > <a href="#" + > <a href="#" title="TypeFamilies" >Test</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -332,6 +320,10 @@ ><details id="i:id:X:Test:3" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p ></details ></td ></tr @@ -342,9 +334,9 @@ ></span > <span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Foo</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -358,14 +350,18 @@ ><details id="i:id:X:Foo:4" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Foo</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > = <a href="#" + > = <a href="#" title="TypeFamilies" >Y</a ></div ></details @@ -378,13 +374,11 @@ ></span > <span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >X</a - > <a href="#" + > <a href="#" title="TypeFamilies" >XXX</a - > <a href="#" + > <a href="#" title="TypeFamilies" + ><></a + > <a href="#" title="TypeFamilies" >XX</a ></span > <a href="#" class="selflink" @@ -398,18 +392,20 @@ ><details id="i:id:X:-60--62-:5" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >X</a - > <a href="#" + > <a href="#" title="TypeFamilies" >XXX</a - > <a href="#" + > <a href="#" title="TypeFamilies" + ><></a + > <a href="#" title="TypeFamilies" >XX</a - > = <a href="#" + > = <a href="#" title="TypeFamilies" >X</a ></div ></details @@ -422,11 +418,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocD</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -440,14 +434,16 @@ ><details id="i:id:X:AssocD:6" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocD</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a > = <a id="v:AssocX" class="def" >AssocX</a @@ -462,11 +458,9 @@ ></span > <span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocT</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -480,22 +474,22 @@ ><details id="i:id:X:AssocT:7" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocT</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > = <a href="#" + > = (<a href="#" title="TypeFamilies" >Foo</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - ></div + > :: *)</div ></details ></td ></tr @@ -506,11 +500,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -526,20 +518,22 @@ ><details id="i:id:X:Bat:8" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a > <ul class="inst" ><li class="inst" >= <a id="v:BatX" class="def" >BatX</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></li ><li class="inst" @@ -549,13 +543,13 @@ ><li ><a id="v:aaa" class="def" >aaa</a - > :: <a href="#" + > :: <a href="#" title="TypeFamilies" >X</a ></li ><li ><a id="v:bbb" class="def" >bbb</a - > :: <a href="#" + > :: <a href="#" title="TypeFamilies" >Y</a ></li ></ul @@ -572,11 +566,9 @@ ></span > <span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Foo</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -590,16 +582,18 @@ ><details id="i:id:X:Foo:9" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Foo</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > = <a href="#" + > = <a href="#" title="TypeFamilies" >Y</a ></div ></details @@ -612,13 +606,11 @@ ></span > <span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > a</span + > <a href="#" title="TypeFamilies" + ><></a + > (a :: *)</span > <a href="#" class="selflink" >#</a ></td @@ -630,16 +622,18 @@ ><details id="i:id:X:-60--62-:10" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > a = <a href="#" + > <a href="#" title="TypeFamilies" + ><></a + > (a :: *) = <a href="#" title="TypeFamilies" >X</a ></div ></details @@ -672,11 +666,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:Y:Assoc:1" ></span - > <a href="#" + > <a href="#" title="TypeFamilies" >Assoc</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -692,35 +684,31 @@ ><details id="i:id:Y:Assoc:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs associated-types" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="subs associated-types" ><p class="caption" >Associated Types</p ><p class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocD</a - > <a href="#" - >Y</a - > (a :: <a href="#" + > <a href="#" title="TypeFamilies" >Y</a - >) :: <a href="#" - >*</a - > <a href="#" class="selflink" + > :: * <a href="#" class="selflink" >#</a ></p ><p class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocT</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a - > (a :: <a href="#" - >Y</a - >) :: <a href="#" - >*</a - > <a href="#" class="selflink" + > :: * <a href="#" class="selflink" >#</a ></p ></div @@ -732,11 +720,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:id:Y:Test:2" ></span - > <a href="#" + > <a href="#" title="TypeFamilies" >Test</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -752,6 +738,10 @@ ><details id="i:id:Y:Test:2" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p ></details ></td ></tr @@ -762,9 +752,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Bar</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -778,12 +768,16 @@ ><details id="i:id:Y:Bar:3" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Bar</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></div ></details @@ -796,11 +790,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocD</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -814,14 +806,16 @@ ><details id="i:id:Y:AssocD:4" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocD</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a > = <a id="v:AssocY" class="def" >AssocY</a @@ -836,11 +830,9 @@ ></span > <span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocT</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -854,20 +846,20 @@ ><details id="i:id:Y:AssocT:5" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocT</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a - > = <a href="#" + > = <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></div ></details @@ -880,11 +872,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -900,18 +890,20 @@ ><details id="i:id:Y:Bat:6" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a > = <a id="v:BatY" class="def" >BatY</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></div ></details @@ -924,11 +916,9 @@ ></span > <span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Foo</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -942,16 +932,18 @@ ><details id="i:id:Y:Foo:7" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Foo</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a - > = <a href="#" + > = <a href="#" title="TypeFamilies" >X</a ></div ></details @@ -964,13 +956,11 @@ ></span > <span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a - > a</span + > <a href="#" title="TypeFamilies" + ><></a + > (a :: *)</span > <a href="#" class="selflink" >#</a ></td @@ -982,16 +972,18 @@ ><details id="i:id:Y:-60--62-:8" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a - > a = a</div + > <a href="#" title="TypeFamilies" + ><></a + > (a :: *) = a</div ></details ></td ></tr @@ -1046,11 +1038,11 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" + > (z :: <a href="#" title="TypeFamilies" >Z</a - ></span + >)</span > <a href="#" class="selflink" >#</a ></td @@ -1064,34 +1056,44 @@ ><details id="i:id:Z:Bat:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" + > (z :: <a href="#" title="TypeFamilies" >Z</a - > <span class="keyword" + >) <span class="keyword" >where</span ><ul class="inst" ><li class="inst" ><a id="v:BatZ1" class="def" >BatZ1</a - > :: <a href="#" - >Bat</a - > <a href="#" + > :: <span class="keyword" + >forall</span + > (z :: <a href="#" title="TypeFamilies" + >Z</a + >). <a href="#" title="TypeFamilies" >Z</a - > <a href="#" + > -> <a href="#" title="TypeFamilies" + >Bat</a + > <a href="#" title="TypeFamilies" >ZA</a ></li ><li class="inst" ><a id="v:BatZ2" class="def" >BatZ2</a - > :: <a href="#" - >Bat</a - > <a href="#" + > :: <span class="keyword" + >forall</span + > (z :: <a href="#" title="TypeFamilies" >Z</a - > <a href="#" + >). {..} -> <a href="#" title="TypeFamilies" + >Bat</a + > <a href="#" title="TypeFamilies" >ZB</a ></li ></ul @@ -1126,11 +1128,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Test:Test:1" ></span - > <a href="#" + > <a href="#" title="TypeFamilies" >Test</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -1146,6 +1146,10 @@ ><details id="i:ic:Test:Test:1" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p ></details ></td ></tr @@ -1154,11 +1158,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Test:Test:2" ></span - > <a href="#" + > <a href="#" title="TypeFamilies" >Test</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -1174,6 +1176,10 @@ ><details id="i:ic:Test:Test:2" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p ></details ></td ></tr @@ -1206,11 +1212,9 @@ ></span > <span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Foo</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -1224,16 +1228,18 @@ ><details id="i:if:Foo:Foo:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Foo</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a - > = <a href="#" + > = <a href="#" title="TypeFamilies" >X</a ></div ></details @@ -1246,11 +1252,9 @@ ></span > <span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Foo</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -1264,16 +1268,18 @@ ><details id="i:if:Foo:Foo:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Foo</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > = <a href="#" + > = <a href="#" title="TypeFamilies" >Y</a ></div ></details @@ -1289,9 +1295,7 @@ >data family</span > <a id="t:Bat" class="def" >Bat</a - > (a :: k) :: <a href="#" - >*</a - > <a href="#" class="selflink" + > (a :: k) :: * <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -1310,11 +1314,11 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" + > (z :: <a href="#" title="TypeFamilies" >Z</a - ></span + >)</span > <a href="#" class="selflink" >#</a ></td @@ -1328,34 +1332,44 @@ ><details id="i:if:Bat:Bat:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" + > (z :: <a href="#" title="TypeFamilies" >Z</a - > <span class="keyword" + >) <span class="keyword" >where</span ><ul class="inst" ><li class="inst" ><a id="v:BatZ1" class="def" >BatZ1</a - > :: <a href="#" - >Bat</a - > <a href="#" + > :: <span class="keyword" + >forall</span + > (z :: <a href="#" title="TypeFamilies" >Z</a - > <a href="#" + >). <a href="#" title="TypeFamilies" + >Z</a + > -> <a href="#" title="TypeFamilies" + >Bat</a + > <a href="#" title="TypeFamilies" >ZA</a ></li ><li class="inst" ><a id="v:BatZ2" class="def" >BatZ2</a - > :: <a href="#" - >Bat</a - > <a href="#" + > :: <span class="keyword" + >forall</span + > (z :: <a href="#" title="TypeFamilies" >Z</a - > <a href="#" + >). {..} -> <a href="#" title="TypeFamilies" + >Bat</a + > <a href="#" title="TypeFamilies" >ZB</a ></li ></ul @@ -1370,11 +1384,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -1390,18 +1402,20 @@ ><details id="i:if:Bat:Bat:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a > = <a id="v:BatY" class="def" >BatY</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></div ></details @@ -1414,11 +1428,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -1434,20 +1446,22 @@ ><details id="i:if:Bat:Bat:3" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >Bat</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a > <ul class="inst" ><li class="inst" >= <a id="v:BatX" class="def" >BatX</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></li ><li class="inst" @@ -1457,13 +1471,13 @@ ><li ><a id="v:aaa" class="def" >aaa</a - > :: <a href="#" + > :: <a href="#" title="TypeFamilies" >X</a ></li ><li ><a id="v:bbb" class="def" >bbb</a - > :: <a href="#" + > :: <a href="#" title="TypeFamilies" >Y</a ></li ></ul @@ -1498,9 +1512,7 @@ >data</span > <a id="t:AssocD" class="def" >AssocD</a - > a :: <a href="#" - >*</a - > <a href="#" class="selflink" + > a :: * <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -1512,9 +1524,7 @@ >type</span > <a id="t:AssocT" class="def" >AssocT</a - > a :: <a href="#" - >*</a - > <a href="#" class="selflink" + > a :: * <a href="#" class="selflink" >#</a ></p ><div class="doc" @@ -1532,11 +1542,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Assoc:Assoc:1" ></span - > <a href="#" + > <a href="#" title="TypeFamilies" >Assoc</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -1552,35 +1560,31 @@ ><details id="i:ic:Assoc:Assoc:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs associated-types" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="subs associated-types" ><p class="caption" >Associated Types</p ><p class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocD</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a - > (a :: <a href="#" - >Y</a - >) :: <a href="#" - >*</a - > <a href="#" class="selflink" + > :: * <a href="#" class="selflink" >#</a ></p ><p class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocT</a - > <a href="#" - >Y</a - > (a :: <a href="#" + > <a href="#" title="TypeFamilies" >Y</a - >) :: <a href="#" - >*</a - > <a href="#" class="selflink" + > :: * <a href="#" class="selflink" >#</a ></p ></div @@ -1592,11 +1596,9 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:Assoc:Assoc:2" ></span - > <a href="#" + > <a href="#" title="TypeFamilies" >Assoc</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -1612,35 +1614,31 @@ ><details id="i:ic:Assoc:Assoc:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="subs associated-types" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="subs associated-types" ><p class="caption" >Associated Types</p ><p class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocD</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > (a :: <a href="#" - >X</a - >) :: <a href="#" - >*</a - > <a href="#" class="selflink" + > :: * <a href="#" class="selflink" >#</a ></p ><p class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies" >AssocT</a - > <a href="#" - >X</a - > (a :: <a href="#" + > <a href="#" title="TypeFamilies" >X</a - >) :: <a href="#" - >*</a - > <a href="#" class="selflink" + > :: * <a href="#" class="selflink" >#</a ></p ></div @@ -1672,11 +1670,11 @@ ><table ><tr ><td class="src" - ><a href="#" + ><a href="#" title="TypeFamilies" >Bar</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > = <a href="#" + > = <a href="#" title="TypeFamilies" >X</a ></td ><td class="doc empty" @@ -1684,9 +1682,9 @@ ></tr ><tr ><td class="src" - ><a href="#" + ><a href="#" title="TypeFamilies" >Bar</a - > y = <a href="#" + > y = <a href="#" title="TypeFamilies" >Y</a ></td ><td class="doc empty" @@ -1716,13 +1714,11 @@ ></span > <span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >X</a - > <a href="#" + > <a href="#" title="TypeFamilies" >XXX</a - > <a href="#" + > <a href="#" title="TypeFamilies" + ><></a + > <a href="#" title="TypeFamilies" >XX</a ></span > <a href="#" class="selflink" @@ -1736,18 +1732,20 @@ ><details id="i:if:-60--62-:-60--62-:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >X</a - > <a href="#" + > <a href="#" title="TypeFamilies" >XXX</a - > <a href="#" + > <a href="#" title="TypeFamilies" + ><></a + > <a href="#" title="TypeFamilies" >XX</a - > = <a href="#" + > = <a href="#" title="TypeFamilies" >X</a ></div ></details @@ -1760,13 +1758,11 @@ ></span > <span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a - > a</span + > <a href="#" title="TypeFamilies" + ><></a + > (a :: *)</span > <a href="#" class="selflink" >#</a ></td @@ -1778,16 +1774,18 @@ ><details id="i:if:-60--62-:-60--62-:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a - > a = a</div + > <a href="#" title="TypeFamilies" + ><></a + > (a :: *) = a</div ></details ></td ></tr @@ -1798,13 +1796,11 @@ ></span > <span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > a</span + > <a href="#" title="TypeFamilies" + ><></a + > (a :: *)</span > <a href="#" class="selflink" >#</a ></td @@ -1816,16 +1812,18 @@ ><details id="i:if:-60--62-:-60--62-:3" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" - >(<>)</a - > <a href="#" - >*</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > a = <a href="#" + > <a href="#" title="TypeFamilies" + ><></a + > (a :: *) = <a href="#" title="TypeFamilies" >X</a ></div ></details @@ -1854,13 +1852,11 @@ ><span class="inst-left" ><span class="instance details-toggle-control details-toggle" data-details-id="i:ic:-62--60-:-62--60-:1" ></span - > <a href="#" - >(><)</a - > <a href="#" - >X</a - > <a href="#" + > <a href="#" title="TypeFamilies" >XX</a - > <a href="#" + > <a href="#" title="TypeFamilies" + >><</a + > <a href="#" title="TypeFamilies" >XXX</a ></span > <a href="#" class="selflink" @@ -1874,6 +1870,10 @@ ><details id="i:ic:-62--60-:-62--60-:1" ><summary class="hide-when-js-enabled" >Instance details</summary + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p ></details ></td ></tr diff --git a/html-test/ref/TypeFamilies2.html b/html-test/ref/TypeFamilies2.html index 84e7df36..a5d0d9a9 100644 --- a/html-test/ref/TypeFamilies2.html +++ b/html-test/ref/TypeFamilies2.html @@ -92,9 +92,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Bar</a - > <a href="#" + > <a href="#" title="TypeFamilies2" >W</a ></span > <a href="#" class="selflink" @@ -110,12 +110,16 @@ ><details id="i:id:W:Bar:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies2</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Bar</a - > <a href="#" + > <a href="#" title="TypeFamilies2" >W</a > = <a id="v:BarX" class="def" >BarX</a @@ -130,9 +134,9 @@ ></span > <span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Foo</a - > <a href="#" + > <a href="#" title="TypeFamilies2" >W</a ></span > <a href="#" class="selflink" @@ -146,12 +150,16 @@ ><details id="i:id:W:Foo:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies2</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Foo</a - > <a href="#" + > <a href="#" title="TypeFamilies2" >W</a ></div ></details @@ -186,9 +194,9 @@ ></span > <span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Foo</a - > <a href="#" + > <a href="#" title="TypeFamilies2" >W</a ></span > <a href="#" class="selflink" @@ -202,12 +210,16 @@ ><details id="i:if:Foo:Foo:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies2</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Foo</a - > <a href="#" + > <a href="#" title="TypeFamilies2" >W</a ></div ></details @@ -220,9 +232,9 @@ ></span > <span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Foo</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a ></span > <a href="#" class="selflink" @@ -236,14 +248,18 @@ ><details id="i:if:Foo:Foo:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >type</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Foo</a - > <a href="#" + > <a href="#" title="TypeFamilies" >X</a - > = <a href="#" + > = <a href="#" title="TypeFamilies" >Y</a ></div ></details @@ -278,9 +294,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Bar</a - > <a href="#" + > <a href="#" title="TypeFamilies2" >W</a ></span > <a href="#" class="selflink" @@ -296,12 +312,16 @@ ><details id="i:if:Bar:Bar:1" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies2</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Bar</a - > <a href="#" + > <a href="#" title="TypeFamilies2" >W</a > = <a id="v:BarX" class="def" >BarX</a @@ -316,9 +336,9 @@ ></span > <span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Bar</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></span > <a href="#" class="selflink" @@ -332,12 +352,16 @@ ><details id="i:if:Bar:Bar:2" ><summary class="hide-when-js-enabled" >Instance details</summary - ><div class="src" + ><p + >Defined in <a href="#" + >TypeFamilies</a + ></p + > <div class="src" ><span class="keyword" >data</span - > <a href="#" + > <a href="#" title="TypeFamilies2" >Bar</a - > <a href="#" + > <a href="#" title="TypeFamilies" >Y</a ></div ></details diff --git a/html-test/ref/TypeOperators.html b/html-test/ref/TypeOperators.html index d389162e..76a5b280 100644 --- a/html-test/ref/TypeOperators.html +++ b/html-test/ref/TypeOperators.html @@ -127,7 +127,7 @@ ><p class="src" ><a id="v:biO" class="def" >biO</a - > :: (g <a href="#" + > :: (g <a href="#" title="TypeOperators" >`O`</a > f) a <a href="#" class="selflink" >#</a @@ -153,11 +153,11 @@ ><p class="src" ><a id="v:x" class="def" >x</a - > :: (a <a href="#" + > :: (a <a href="#" title="TypeOperators" >:-:</a - > a) <a href="#" + > a) <a href="#" title="TypeOperators" ><=></a - > (a <a href="#" + > (a <a href="#" title="TypeOperators" >`Op`</a > a) => a <a href="#" class="selflink" >#</a @@ -167,11 +167,11 @@ ><p class="src" ><a id="v:y" class="def" >y</a - > :: (a <a href="#" + > :: (a <a href="#" title="TypeOperators" ><=></a - > a, (a <a href="#" + > a, (a <a href="#" title="TypeOperators" >`Op`</a - > a) <a href="#" + > a) <a href="#" title="TypeOperators" ><=></a > a) => a <a href="#" class="selflink" >#</a diff --git a/html-test/ref/Unicode.html b/html-test/ref/Unicode.html index 0f2a30d4..3cae7357 100644 --- a/html-test/ref/Unicode.html +++ b/html-test/ref/Unicode.html @@ -46,9 +46,7 @@ ><li class="src short" ><a href="#" >x</a - > :: <a href="#" - >Int</a - ></li + > :: Int</li ></ul ></details ></div @@ -59,9 +57,7 @@ ><p class="src" ><a id="v:x" class="def" >x</a - > :: <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int <a href="#" class="selflink" >#</a ></p ><div class="doc" diff --git a/html-test/ref/Visible.html b/html-test/ref/Visible.html index dad23fef..22c6be6c 100644 --- a/html-test/ref/Visible.html +++ b/html-test/ref/Visible.html @@ -45,11 +45,7 @@ ><p class="src" ><a id="v:visible" class="def" >visible</a - > :: <a href="#" - >Int</a - > -> <a href="#" - >Int</a - > <a href="#" class="selflink" + > :: Int -> Int <a href="#" class="selflink" >#</a ></p ></div diff --git a/html-test/src/Bug458.hs b/html-test/src/Bug458.hs new file mode 100644 index 00000000..6a3ac9a4 --- /dev/null +++ b/html-test/src/Bug458.hs @@ -0,0 +1,6 @@ +module Bug458 where + +-- | See the defn of @'⊆'@. +(⊆) :: () -> () -> () +_ ⊆ _ = () + diff --git a/html-test/src/Bug546.hs b/html-test/src/Bug546.hs new file mode 100644 index 00000000..4493b1d9 --- /dev/null +++ b/html-test/src/Bug546.hs @@ -0,0 +1,55 @@ +module Bug546 where + +-- |Test: +-- +-- [@[code with square \\ brackets\]@] lorem ipsum +x = 1 + +-- | +-- +-- [@[..\]@] Matches any of the enclosed characters. Ranges of characters can +-- be specified by separating the endpoints with a @\'-'@. @\'-'@ or +-- @']'@ can be matched by including them as the first character(s) +-- in the list. Never matches path separators: @[\/]@ matches +-- nothing at all. Named character classes can also be matched: +-- @[:x:]@ within @[]@ specifies the class named @x@, which matches +-- certain predefined characters. See below for a full list. +-- +-- [@[^..\]@ or @[!..\]@] Like @[..]@, but matches any character /not/ listed. +-- Note that @[^-x]@ is not the inverse of @[-x]@, but +-- the range @[^-x]@. +-- +-- [@\<m-n>@] Matches any integer in the range m to n, inclusive. The range may +-- be open-ended by leaving out either number: @\"\<->\"@, for +-- instance, matches any integer. +-- +-- [@**/@] Matches any number of characters, including path separators, +-- excluding the empty string. +-- +-- Supported character classes: +-- +-- [@[:alnum:\]@] Equivalent to @\"0-9A-Za-z\"@. +-- +-- [@[:alpha:\]@] Equivalent to @\"A-Za-z\"@. +-- +-- [@[:blank:\]@] Equivalent to @\"\\t \"@. +-- +-- [@[:cntrl:\]@] Equivalent to @\"\\0-\\x1f\\x7f\"@. +-- +-- [@[:digit:\]@] Equivalent to @\"0-9\"@. +-- +-- [@[:graph:\]@] Equivalent to @\"!-~\"@. +-- +-- [@[:lower:\]@] Equivalent to @\"a-z\"@. +-- +-- [@[:print:\]@] Equivalent to @\" -~\"@. +-- +-- [@[:punct:\]@] Equivalent to @\"!-\/:-\@[-`{-~\"@. +-- +-- [@[:space:\]@] Equivalent to @\"\\t-\\r \"@. +-- +-- [@[:upper:\]@] Equivalent to @\"A-Z\"@. +-- +-- [@[:xdigit:\]@] Equivalent to @\"0-9A-Fa-f\"@. +compile :: String -> String +compile = id
\ No newline at end of file diff --git a/html-test/src/Bug548.hs b/html-test/src/Bug548.hs new file mode 100644 index 00000000..652d3d32 --- /dev/null +++ b/html-test/src/Bug548.hs @@ -0,0 +1,3 @@ +module Bug548 (WrappedArrow(..)) where + +import Control.Applicative diff --git a/html-test/src/Bug679.hs b/html-test/src/Bug679.hs new file mode 100644 index 00000000..dba194c4 --- /dev/null +++ b/html-test/src/Bug679.hs @@ -0,0 +1,24 @@ +{-# LANGUAGE TemplateHaskell #-} + +module Bug679 where + +import Language.Haskell.TH + +data Bar a = Bar + +$(do + a <- newName "a" + + let classN = mkName "Foo" + let methodN = mkName "foo" + + methodTy <- [t| $(varT a) -> $(varT a) |] + let cla = ClassD [] classN [PlainTV a] [] [SigD methodN methodTy] + + -- Note that we are /reusing/ the same type variable 'a' as in the class + instanceHead <- [t| $(conT classN) (Bar $(varT a)) |] + idCall <- [e| id |] + let ins = InstanceD Nothing [] instanceHead [FunD methodN [Clause [] (NormalB idCall) []]] + + pure [cla,ins]) + diff --git a/html-test/src/Table.hs b/html-test/src/Table.hs new file mode 100644 index 00000000..2cf0c662 --- /dev/null +++ b/html-test/src/Table.hs @@ -0,0 +1,47 @@ +-- | This tests the table markup +module Table + ( tableWithHeader + , tableWithoutHeader + , fancyTable + ) where + +-- | Table with header. +-- +-- +------+--------------+------------------------------------------+ +-- | code | message | description | +-- +======+==============+==========================================+ +-- | 200 | @OK@ | operation successful | +-- +------+--------------+------------------------------------------+ +-- | 204 | @No Content@ | operation successful, no body returned | +-- +------+--------------+------------------------------------------+ +tableWithHeader :: a -> a +tableWithHeader a = a + +-- | Table without header. +-- +-- +------+--------------+------------------------------------------+ +-- | 200 | @OK@ | operation successful | +-- +------+--------------+------------------------------------------+ +-- | 204 | @No Content@ | operation successful, no body returned | +-- +------+--------------+------------------------------------------+ +-- | 404 | @Not Found@ | resource not found | +-- +------+--------------+------------------------------------------+ +tableWithoutHeader :: a -> a +tableWithoutHeader a = a + +-- | Fancy table. +-- +-- +------------------------+------------+----------+----------+ +-- | Header row, column 1 | Header 2 | Header 3 | Header 4 | +-- | (header rows optional) | | | | +-- +========================+============+==========+==========+ +-- | body row 1, column 1 | column 2 | column 3 | column 4 | +-- +------------------------+------------+----------+----------+ +-- | 'tableWithHeader' | Cells may span columns. | +-- +------------------------+------------+---------------------+ +-- | body row 3 | Cells may | \[ | +-- +------------------------+ span rows. | f(n) = \sum_{i=1} | +-- | body row 4 | | \] | +-- +------------------------+------------+---------------------+ +fancyTable :: a -> a +fancyTable x = x diff --git a/hypsrc-test/ref/src/CPP.html b/hypsrc-test/ref/src/CPP.html new file mode 100644 index 00000000..fb85bd2f --- /dev/null +++ b/hypsrc-test/ref/src/CPP.html @@ -0,0 +1,216 @@ +<html xmlns="http://www.w3.org/1999/xhtml" +><head + ><link rel="stylesheet" type="text/css" href="style.css" + /><script type="text/javascript" src="highlight.js" + ></script + ></head + ><body + ><pre + ><span class="hs-pragma" + >{-# LANGUAGE CPP #-}</span + ><span + > +</span + ><a name="line-2" + ></a + ><span class="hs-keyword" + >module</span + ><span + > </span + ><span class="hs-identifier" + >CPP</span + ><span + > </span + ><span class="hs-keyword" + >where</span + ><span + > +</span + ><a name="line-3" + ></a + ><span + > +</span + ><a name="line-4" + ></a + ><span class="hs-cpp" + >#define SOMETHING1 +</span + ><span + > +</span + ><a name="line-6" + ></a + ><span class="hs-identifier" + >foo</span + ><span + > </span + ><span class="hs-glyph" + >::</span + ><span + > </span + ><span class="hs-identifier hs-type" + >String</span + ><span + > +</span + ><a name="line-7" + ></a + ><a name="foo" + ><a href="CPP.html#foo" + ><span class="hs-identifier" + >foo</span + ></a + ></a + ><span + > </span + ><span class="hs-glyph" + >=</span + ><span + > </span + ><span class="hs-comment" + >{- " single quotes are fine in block comments + {- nested block comments are fine -} + -}</span + ><span + > </span + ><span class="hs-string" + >"foo"</span + ><span + > +</span + ><a name="line-10" + ></a + ><span + > +</span + ><a name="line-11" + ></a + ><span class="hs-cpp" + >#define SOMETHING2 +</span + ><span + > +</span + ><a name="line-13" + ></a + ><span class="hs-identifier" + >bar</span + ><span + > </span + ><span class="hs-glyph" + >::</span + ><span + > </span + ><span class="hs-identifier hs-type" + >String</span + ><span + > +</span + ><a name="line-14" + ></a + ><a name="bar" + ><a href="CPP.html#bar" + ><span class="hs-identifier" + >bar</span + ></a + ></a + ><span + > </span + ><span class="hs-glyph" + >=</span + ><span + > </span + ><span class="hs-string" + >"block comment in a string is not a comment {- "</span + ><span + > +</span + ><a name="line-15" + ></a + ><span + > +</span + ><a name="line-16" + ></a + ><span class="hs-cpp" + >#define SOMETHING3 +</span + ><span + > +</span + ><a name="line-18" + ></a + ><span class="hs-comment" + >-- " single quotes are fine in line comments</span + ><span + > +</span + ><a name="line-19" + ></a + ><span class="hs-comment" + >-- {- unclosed block comments are fine in line comments</span + ><span + > +</span + ><a name="line-20" + ></a + ><span + > +</span + ><a name="line-21" + ></a + ><span class="hs-comment" + >-- Multiline CPP is also fine</span + ><span + > +</span + ><a name="line-22" + ></a + ><span class="hs-cpp" + >#define FOO\ + 1 +</span + ><span + > +</span + ><a name="line-25" + ></a + ><span class="hs-identifier" + >baz</span + ><span + > </span + ><span class="hs-glyph" + >::</span + ><span + > </span + ><span class="hs-identifier hs-type" + >String</span + ><span + > +</span + ><a name="line-26" + ></a + ><a name="baz" + ><a href="CPP.html#baz" + ><span class="hs-identifier" + >baz</span + ></a + ></a + ><span + > </span + ><span class="hs-glyph" + >=</span + ><span + > </span + ><span class="hs-string" + >"line comment in a string is not a comment --"</span + ><span + > +</span + ><a name="line-27" + ></a + ></pre + ></body + ></html +>
\ No newline at end of file diff --git a/hypsrc-test/ref/src/Classes.html b/hypsrc-test/ref/src/Classes.html index abff8877..d2604e82 100644 --- a/hypsrc-test/ref/src/Classes.html +++ b/hypsrc-test/ref/src/Classes.html @@ -60,8 +60,12 @@ ></a ><span > </span - ><span class="hs-identifier" - >bar</span + ><a name="bar" + ><a href="Classes.html#bar" + ><span class="hs-identifier" + >bar</span + ></a + ></a ><span > </span ><span class="hs-glyph" @@ -87,8 +91,12 @@ ></a ><span > </span - ><span class="hs-identifier" - >baz</span + ><a name="baz" + ><a href="Classes.html#baz" + ><span class="hs-identifier" + >baz</span + ></a + ></a ><span > </span ><span class="hs-glyph" @@ -361,8 +369,12 @@ ></a ><span > </span - ><span class="hs-identifier" - >quux</span + ><a name="quux" + ><a href="Classes.html#quux" + ><span class="hs-identifier" + >quux</span + ></a + ></a ><span > </span ><span class="hs-glyph" @@ -470,8 +482,12 @@ ></a ><span > </span - ><span class="hs-identifier" - >norf</span + ><a name="norf" + ><a href="Classes.html#norf" + ><span class="hs-identifier" + >norf</span + ></a + ></a ><span > </span ><span class="hs-glyph" @@ -703,8 +719,12 @@ ></a ><span > </span - ><span class="hs-identifier" - >plugh</span + ><a name="plugh" + ><a href="Classes.html#plugh" + ><span class="hs-identifier" + >plugh</span + ></a + ></a ><span > </span ><span class="hs-glyph" diff --git a/hypsrc-test/ref/src/Identifiers.html b/hypsrc-test/ref/src/Identifiers.html index f52db4ab..ce69ad37 100644 --- a/hypsrc-test/ref/src/Identifiers.html +++ b/hypsrc-test/ref/src/Identifiers.html @@ -827,11 +827,7 @@ > </span ><a href="Identifiers.html#norf" ><span class="hs-identifier hs-var" - >Identifiers</span - ><span class="hs-operator hs-var" - >.</span - ><span class="hs-identifier hs-var" - >norf</span + >Identifiers.norf</span ></a ><span > </span @@ -931,4 +927,4 @@ ></pre ></body ></html ->
\ No newline at end of file +> diff --git a/hypsrc-test/src/CPP.hs b/hypsrc-test/src/CPP.hs new file mode 100644 index 00000000..f00ce031 --- /dev/null +++ b/hypsrc-test/src/CPP.hs @@ -0,0 +1,26 @@ +{-# LANGUAGE CPP #-} +module CPP where + +#define SOMETHING1 + +foo :: String +foo = {- " single quotes are fine in block comments + {- nested block comments are fine -} + -} "foo" + +#define SOMETHING2 + +bar :: String +bar = "block comment in a string is not a comment {- " + +#define SOMETHING3 + +-- " single quotes are fine in line comments +-- {- unclosed block comments are fine in line comments + +-- Multiline CPP is also fine +#define FOO\ + 1 + +baz :: String +baz = "line comment in a string is not a comment --" |