├── .Rbuildignore
├── .gitignore
├── DESCRIPTION
├── LICENSE
├── LICENSE.md
├── NAMESPACE
├── R
└── betterposter.R
├── README.md
├── betterposter.Rproj
├── inst
├── resources
│ ├── betterposter.css
│ ├── betterposter.html
│ └── qrcode.min.js
└── rmarkdown
│ └── templates
│ └── betterposter
│ ├── skeleton
│ └── skeleton.Rmd
│ └── template.yaml
└── man
├── figures
└── betterposter-example.png
└── poster_better.Rd
/.Rbuildignore:
--------------------------------------------------------------------------------
1 | ^LICENSE\.md$
2 | ^betterposter\.Rproj$
3 | ^\.Rproj\.user$
4 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # ---- Default .gitignore From grkmisc ----
2 | .Rproj.user
3 | .Rhistory
4 | .RData
5 | .DS_Store
6 |
7 | # Directories that start with _
8 | _*/
9 |
10 | ## https://github.com/github/gitignore/blob/master/R.gitignore
11 | # History files
12 | .Rhistory
13 | .Rapp.history
14 |
15 | # Session Data files
16 | .RData
17 |
18 | # Example code in package build process
19 | *-Ex.R
20 |
21 | # Output files from R CMD build
22 | /*.tar.gz
23 |
24 | # Output files from R CMD check
25 | /*.Rcheck/
26 |
27 | # RStudio files
28 | .Rproj.user/
29 |
30 | # produced vignettes
31 | vignettes/*.html
32 | vignettes/*.pdf
33 |
34 | # OAuth2 token, see https://github.com/hadley/httr/releases/tag/v0.3
35 | .httr-oauth
36 |
37 | # knitr and R markdown default cache directories
38 | /*_cache/
39 | /cache/
40 |
41 | # Temporary files created by R markdown
42 | *.utf8.md
43 | *.knit.md
44 |
45 | # Shiny token, see https://shiny.rstudio.com/articles/shinyapps.html
46 | rsconnect/
47 |
48 | ## https://github.com/github/gitignore/blob/master/Global/macOS.gitignore
49 | # General
50 | .DS_Store
51 | .AppleDouble
52 | .LSOverride
53 |
54 | # Icon must end with two \r
55 | Icon
56 |
57 |
58 | # Thumbnails
59 | ._*
60 |
61 | # Files that might appear in the root of a volume
62 | .DocumentRevisions-V100
63 | .fseventsd
64 | .Spotlight-V100
65 | .TemporaryItems
66 | .Trashes
67 | .VolumeIcon.icns
68 | .com.apple.timemachine.donotpresent
69 |
70 | # Directories potentially created on remote AFP share
71 | .AppleDB
72 | .AppleDesktop
73 | Network Trash Folder
74 | Temporary Items
75 | .apdisk
76 |
--------------------------------------------------------------------------------
/DESCRIPTION:
--------------------------------------------------------------------------------
1 | Package: betterposter
2 | Title: A Better Scientific Poster
3 | Version: 0.0.1
4 | Authors@R:
5 | person(given = "Garrick",
6 | family = "Aden-Buie",
7 | role = c("aut", "cre"),
8 | email = "garrick@adenbuie.com")
9 | Description: A better scientific poster using the best markdown
10 | technology available.
11 | License: MIT + file LICENSE
12 | Imports:
13 | htmltools,
14 | pagedown,
15 | utils
16 | Encoding: UTF-8
17 | LazyData: true
18 | Roxygen: list(markdown = TRUE)
19 | RoxygenNote: 6.1.1
20 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | YEAR: 2019
2 | COPYRIGHT HOLDER: Garrick Aden-Buie
3 |
--------------------------------------------------------------------------------
/LICENSE.md:
--------------------------------------------------------------------------------
1 | # MIT License
2 |
3 | Copyright (c) 2019 Garrick Aden-Buie
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/NAMESPACE:
--------------------------------------------------------------------------------
1 | # Generated by roxygen2: do not edit by hand
2 |
3 | export(poster_better)
4 | export(qrcode_options)
5 |
--------------------------------------------------------------------------------
/R/betterposter.R:
--------------------------------------------------------------------------------
1 | #' Create a Better Poster in HTML
2 | #'
3 | #' @return An R Markdown output format.
4 | #' @export
5 | poster_better <- function(
6 | ...,
7 | css = NULL,
8 | height = NULL,
9 | width = NULL,
10 | hero_background = NULL,
11 | hero_color = NULL,
12 | qrcode = NULL,
13 | logo = NULL,
14 | accent_color = NULL,
15 | mathjax = FALSE,
16 | pandoc_args = NULL
17 | ) {
18 | template <- pkg_resource("betterposter.html")
19 |
20 | if (!is.null(qrcode)) {
21 | if (inherits(qrcode, "list")) {
22 | if (!"color_background" %in% names(qrcode) && !is.null(hero_background)) {
23 | qrcode$color_background <- hero_background
24 | }
25 | if (!"color" %in% names(qrcode) && !is.null(hero_color)) {
26 | qrcode$color <- hero_color
27 | }
28 | qrcode <- do.call("qrcode_options", qrcode)
29 | } else if (is.character(qrcode) && length(qrcode) == 1) {
30 | qrcode <- qrcode_options(qrcode, color_background = hero_background)
31 | }
32 | if (!inherits(qrcode, "qrcode")) {
33 | stop("Please use qrcode_options() to set qrcode")
34 | }
35 | }
36 |
37 | pandoc_args <- c(pandoc_args, pandoc_arg(c(
38 | height = if (!is.null(height)) paste0(height, "in"),
39 | width = if (!is.null(width)) paste0(width, "in"),
40 | hero_background = hero_background,
41 | hero_color = hero_color,
42 | logo = logo,
43 | accent_color = accent_color
44 | )))
45 |
46 | if (mathjax) pandoc_args <- c(pandoc_args, "--mathjax")
47 |
48 | pagedown::poster_relaxed(..., css = css, template = template,
49 | .dependencies = betterposter_dependencies(),
50 | pandoc_args = c(pandoc_args, qrcode),
51 | md_extensions = "-autolink_bare_uris",
52 | number_sections = FALSE)
53 | }
54 |
55 | #' @export
56 | qrcode_options <- function(
57 | text,
58 | color_background = "#00000000",
59 | color = "#FFFFFF",
60 | size = "250",
61 | as_yaml = FALSE
62 | ) {
63 | stopifnot(is.character(text))
64 | stopifnot(is.character(color_background))
65 | stopifnot(is.character(color))
66 | stopifnot(is.character(size))
67 |
68 | # if color_background is not a hex color then set to inherit
69 | color_background <- trimws(color_background)
70 | if (sub("#[a-fA-F0-9]{4,6}", "", color_background) != "") {
71 | warning("Ignoring non-hex QR code background in `color_background`")
72 | color_background <- "#00000000"
73 | }
74 |
75 | if (as_yaml) {
76 | x <- paste0(
77 | "\nqrcode:",
78 | '\n text: "', text, '"',
79 | '\n color_background: "', color_background, '"',
80 | '\n color: "', color, '"',
81 | '\n size: "', size, '"'
82 | )
83 | cat(x)
84 | return(invisible(x))
85 | }
86 |
87 | x <- pandoc_arg(c(
88 | "qrcode_text" = text,
89 | "qrcode_color_background" = color_background,
90 | "qrcode_color" = color,
91 | "qrcode_size" = size
92 | ))
93 | class(x) <- c("qrcode", class(x))
94 | x
95 | }
96 |
97 |
98 |
99 | # Utils -------------------------------------------------------------------
100 | pkg_resource = function(...) {
101 | system.file('resources', ..., package = 'betterposter', mustWork = TRUE)
102 | }
103 |
104 | pandoc_arg <- function(values) {
105 | if (is.null(values) || length(values) == 0) return(NULL)
106 | stopifnot(!is.null(names(values)))
107 | ret <- c()
108 | for (name in names(values)) {
109 | ret <- c(
110 | ret,
111 | "--variable",
112 | paste0(name, "=", values[name])
113 | )
114 | }
115 | ret
116 | }
117 |
118 | betterposter_dependencies <- function() {
119 | list(
120 | htmltools::htmlDependency(
121 | "betterposter",
122 | packageVersion("betterposter"),
123 | src = pkg_resource(),
124 | stylesheet = "betterposter.css"
125 | ),
126 | htmltools::htmlDependency(
127 | "qrcode",
128 | "0.0.0",
129 | src = pkg_resource(),
130 | script = "qrcode.min.js"
131 | )
132 | )
133 | }
134 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # betterposter
2 |
3 | ### Another Better Scientific Poster Using R Markdown and pagedown
4 |
5 |
6 |
7 |
8 | [mikemorrison-betterposter]: https://osf.io/ef53g/
9 | [posterdown]: https://brentthorne.github.io/posterdown_html_showcase/
10 |
11 | ⚠️ *This is a work in progress and is not fully documented yet* ⚠️
12 |
13 | A better scientific poster, inspired by [Mike Morrison's Better Poster Template][mikemorrison-betterposter].
14 |
15 | ## Installation
16 |
17 | You can install the in-development version of **betterposter** from GitHub with:
18 |
19 | ``` r
20 | # install.packages("devtools")
21 | devtools::install_github("gerkelab/betterposter")
22 | ```
23 |
24 | ## Usage
25 |
26 | Use `betterposter::poster_better()` to get an awesome poster generated from R Markdown!
27 |
28 | 
29 |
30 | ## Features
31 |
32 | Like many others, we saw Mike's [How to create a better research poster in less time](https://youtu.be/1RwJbhkCA58) video on Twitter and loved it. Like others, we thought: "let's bring that to R Markdown!". This is our version, but you may want to check out [posterdown] by Brent Thorne, where another version of the Better Scientific Poster can be found (including a portrait version).
33 |
34 | The main features of this implementation are
35 |
36 | 1. The QR Code is fully customizable and generated in the browser (no external API calls!).
37 | Use `qrcode_options()` to set the `qrcode` argument in `poster_better()`.
38 |
39 | 1. Great default typography built using Roboto and Robot slab for highly readable text and headers, with Source Sans Pro for the main hero text and Source Code Pro for source code (naturally).
40 |
41 | 1. Customizable colors via `hero_background`, `hero_color` and `accent_color`.
42 |
43 | 1. All variables for customizing the poster are listed and (will be) documented in `better_poster()`.
44 |
--------------------------------------------------------------------------------
/betterposter.Rproj:
--------------------------------------------------------------------------------
1 | Version: 1.0
2 |
3 | RestoreWorkspace: No
4 | SaveWorkspace: No
5 | AlwaysSaveHistory: Default
6 |
7 | EnableCodeIndexing: Yes
8 | UseSpacesForTab: Yes
9 | NumSpacesForTab: 2
10 | Encoding: UTF-8
11 |
12 | RnwWeave: Sweave
13 | LaTeX: pdfLaTeX
14 |
15 | AutoAppendNewline: Yes
16 | StripTrailingWhitespace: Yes
17 |
18 | BuildType: Package
19 | PackageUseDevtools: Yes
20 | PackageInstallArgs: --no-multiarch --with-keep.source
21 | PackageRoxygenize: rd,collate,namespace
22 |
--------------------------------------------------------------------------------
/inst/resources/betterposter.css:
--------------------------------------------------------------------------------
1 | @import url('https://fonts.googleapis.com/css?family=Roboto%7CRoboto+Slab:700%7CSource+Code+Pro%7CSource+Sans+Pro:300,700');
2 |
3 | @page {
4 | width: 46.8in;
5 | height: 33.1in;
6 | margin: 0;
7 | }
8 | html, body {
9 | background: #fff;
10 | }
11 | html {
12 | font-family: "Roboto";
13 | font-size: 24px;
14 | color: #333;
15 | width: 46.8in;
16 | height: 33.09669in;
17 | }
18 | body {
19 | margin: 0;
20 | width: 46.3in;
21 | height: 32.59669in;
22 | display: grid;
23 | grid-gap: 0.25in;
24 | grid-template-columns: 60px 60px;
25 | padding: 0.25in !important;
26 | }
27 |
28 | /* ---- Grid ---- */
29 | body {
30 | grid-template-areas:
31 | "T H R"
32 | "L H R"
33 | "L H F";
34 | grid-template-columns: 1fr 3fr 1fr;
35 | grid-template-rows: 1fr 5fr 1fr;
36 | }
37 |
38 | #hero {
39 | grid-area: H;
40 | }
41 |
42 | #left-bar {
43 | grid-area: L;
44 | }
45 |
46 | #right-bar {
47 | grid-area: R;
48 | }
49 | #title-container {
50 | grid-area: T;
51 | }
52 | #references {
53 | grid-area: F;
54 | }
55 |
56 | img {
57 | max-width: 100%;
58 | }
59 |
60 | /* ---- General ---- */
61 | h1, h2, h3, h4 {
62 | margin-block-end: 0;
63 | font-family: "Roboto Slab", Arial, sans-serif;
64 | }
65 | p {
66 | margin-block-start: 0.25em;
67 | }
68 | pre, pre.sourceCode {
69 | font-size: 0.8em;
70 | margin: 1em 0;
71 | padding: 0.5em 0.5em;
72 | }
73 | code {
74 | font-family: "Source Code Pro", Monaco, monospace;
75 | }
76 | blockquote {
77 | font-style: italic;
78 | padding-left: 1em;
79 | border-left: 5pt solid #dadada;
80 | margin-left: 0;
81 | }
82 | sup {
83 | font-size: 0.75em;
84 | font-style: normal;
85 | margin-left: 4pt;
86 | }
87 |
88 | /* ---- Hero ---- */
89 | #hero {
90 | position: relative;
91 | background: #0F5D4F;
92 | color: #fff;
93 | font-family: "Source Sans Pro", "Helvetica Neue", Arial, sans-serif;
94 | padding: 10%;
95 | font-size: 48px;
96 | }
97 |
98 | #hero h1 {
99 | font-family: "Source Sans Pro", "Helvetica Neue", Arial, sans-serif;
100 | font-size: 3.25em;
101 | font-weight: 400;
102 | padding-top: %;
103 | }
104 |
105 | #hero h1 strong {
106 | font-weight: 700;
107 | }
108 |
109 | #hero p {
110 | padding: 10pt 0;
111 | }
112 |
113 | #hero > p:first-of-type {
114 | padding-top: 6em;
115 | }
116 |
117 | #hero img.qrcode {
118 | position: absolute;
119 | bottom: 5%;
120 | }
121 |
122 | #qrcode {
123 | position: absolute;
124 | bottom: 5%;
125 | left: 10%;
126 | }
127 |
128 | /* ---- Social ---- */
129 |
130 | /* ---- Title ---- */
131 | #title-container {
132 | padding: 5% 5% 0 5%;
133 | background: none;
134 | }
135 |
136 | #title-container .author, #title-container .affiliation {
137 | color: #888;
138 | font-family: "Roboto", "Helvetica Neue", Arial, sans-serif;
139 | }
140 | #title-container .author {
141 | font-style: italic;
142 | font-size: 1.25em;
143 | }
144 | #title-container .affiliation {
145 | font-weight: normal;
146 | }
147 |
148 | /* ---- Silent Bar (Left Bar) ---- */
149 | #left-bar {
150 | background: none;
151 | padding: 0 5%;
152 | }
153 |
154 | /* ---- Ammo Bar (Right Bar) ---- */
155 | #right-bar {
156 | background: #fff;
157 | padding: 5%;
158 | }
159 |
160 | /* ---- References ---- */
161 | #references {
162 | padding: 0 5%;
163 | }
164 | #references p, #references ul, #references ol {
165 | font-size: 0.6em;
166 | }
167 |
168 | /* ---- Tables ---- */
169 | table {
170 | border-collapse: collapse;
171 | border-spacing: 0;
172 | text-align: left;
173 | width: 100%;
174 | border: .05rem solid #dadada;
175 | }
176 | table thead {
177 | background: #dadada;
178 | }
179 | table td,
180 | table th {
181 | padding: .1rem .2rem;
182 | font-size: small;
183 | }
184 |
185 | table th {
186 | border-bottom-width: .1rem;
187 | }
188 |
--------------------------------------------------------------------------------
/inst/resources/betterposter.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 | $for(author-meta)$ $endfor$
10 | $if(date-meta)$ $endif$
11 | $if(title-prefix)$$title-prefix$ - $endif$$pagetitle$
12 |
13 | $for(header-includes)$
14 | $header-includes$
15 | $endfor$
16 |
17 | $if(highlightjs)$
18 |
19 |
20 |
21 | $endif$
22 |
23 | $if(highlighting-css)$$endif$
24 |
25 | $for(css)$
26 |
27 | $endfor$
28 |
29 |
74 |
75 |
76 |
77 |
78 | $for(include-before)$
79 | $include-before$
80 | $endfor$
81 |
82 | $if(title)$
83 |
84 |
$title$
85 | $if(author)$
86 |
87 | $for(author)$$author.name$ $if(author.affiliation)$$author.affiliation$ $endif$$if(author.extra)$ ($for(author.extra)$$author.extra$$sep$, $endfor$)$endif$$sep$, $endfor$
88 |
89 | $endif$
90 | $if(affiliation)$
91 |
92 |
93 | $for(affiliation)$
94 | $affiliation$
95 | $endfor$
96 |
97 |
98 | $endif$
99 |
100 | $endif$
101 |
102 | $body$
103 |
104 |
114 |
115 | $if(math)$
116 |
117 |
129 | $endif$
130 |
131 | $if(qrcode_text)$
132 |
149 | $endif$
150 |
151 | $for(include-after)$
152 | $include-after$
153 | $endfor$
154 |
155 |
156 |
157 |
--------------------------------------------------------------------------------
/inst/resources/qrcode.min.js:
--------------------------------------------------------------------------------
1 | var QRCode;!function(){function a(a){this.mode=c.MODE_8BIT_BYTE,this.data=a,this.parsedData=[];for(var b=[],d=0,e=this.data.length;e>d;d++){var f=this.data.charCodeAt(d);f>65536?(b[0]=240|(1835008&f)>>>18,b[1]=128|(258048&f)>>>12,b[2]=128|(4032&f)>>>6,b[3]=128|63&f):f>2048?(b[0]=224|(61440&f)>>>12,b[1]=128|(4032&f)>>>6,b[2]=128|63&f):f>128?(b[0]=192|(1984&f)>>>6,b[1]=128|63&f):b[0]=f,this.parsedData=this.parsedData.concat(b)}this.parsedData.length!=this.data.length&&(this.parsedData.unshift(191),this.parsedData.unshift(187),this.parsedData.unshift(239))}function b(a,b){this.typeNumber=a,this.errorCorrectLevel=b,this.modules=null,this.moduleCount=0,this.dataCache=null,this.dataList=[]}function i(a,b){if(void 0==a.length)throw new Error(a.length+"/"+b);for(var c=0;c=f;f++){var h=0;switch(b){case d.L:h=l[f][0];break;case d.M:h=l[f][1];break;case d.Q:h=l[f][2];break;case d.H:h=l[f][3]}if(h>=e)break;c++}if(c>l.length)throw new Error("Too long data");return c}function s(a){var b=encodeURI(a).toString().replace(/\%[0-9a-fA-F]{2}/g,"a");return b.length+(b.length!=a?3:0)}a.prototype={getLength:function(){return this.parsedData.length},write:function(a){for(var b=0,c=this.parsedData.length;c>b;b++)a.put(this.parsedData[b],8)}},b.prototype={addData:function(b){var c=new a(b);this.dataList.push(c),this.dataCache=null},isDark:function(a,b){if(0>a||this.moduleCount<=a||0>b||this.moduleCount<=b)throw new Error(a+","+b);return this.modules[a][b]},getModuleCount:function(){return this.moduleCount},make:function(){this.makeImpl(!1,this.getBestMaskPattern())},makeImpl:function(a,c){this.moduleCount=4*this.typeNumber+17,this.modules=new Array(this.moduleCount);for(var d=0;d=7&&this.setupTypeNumber(a),null==this.dataCache&&(this.dataCache=b.createData(this.typeNumber,this.errorCorrectLevel,this.dataList)),this.mapData(this.dataCache,c)},setupPositionProbePattern:function(a,b){for(var c=-1;7>=c;c++)if(!(-1>=a+c||this.moduleCount<=a+c))for(var d=-1;7>=d;d++)-1>=b+d||this.moduleCount<=b+d||(this.modules[a+c][b+d]=c>=0&&6>=c&&(0==d||6==d)||d>=0&&6>=d&&(0==c||6==c)||c>=2&&4>=c&&d>=2&&4>=d?!0:!1)},getBestMaskPattern:function(){for(var a=0,b=0,c=0;8>c;c++){this.makeImpl(!0,c);var d=f.getLostPoint(this);(0==c||a>d)&&(a=d,b=c)}return b},createMovieClip:function(a,b,c){var d=a.createEmptyMovieClip(b,c),e=1;this.make();for(var f=0;f=g;g++)for(var h=-2;2>=h;h++)this.modules[d+g][e+h]=-2==g||2==g||-2==h||2==h||0==g&&0==h?!0:!1}},setupTypeNumber:function(a){for(var b=f.getBCHTypeNumber(this.typeNumber),c=0;18>c;c++){var d=!a&&1==(1&b>>c);this.modules[Math.floor(c/3)][c%3+this.moduleCount-8-3]=d}for(var c=0;18>c;c++){var d=!a&&1==(1&b>>c);this.modules[c%3+this.moduleCount-8-3][Math.floor(c/3)]=d}},setupTypeInfo:function(a,b){for(var c=this.errorCorrectLevel<<3|b,d=f.getBCHTypeInfo(c),e=0;15>e;e++){var g=!a&&1==(1&d>>e);6>e?this.modules[e][8]=g:8>e?this.modules[e+1][8]=g:this.modules[this.moduleCount-15+e][8]=g}for(var e=0;15>e;e++){var g=!a&&1==(1&d>>e);8>e?this.modules[8][this.moduleCount-e-1]=g:9>e?this.modules[8][15-e-1+1]=g:this.modules[8][15-e-1]=g}this.modules[this.moduleCount-8][8]=!a},mapData:function(a,b){for(var c=-1,d=this.moduleCount-1,e=7,g=0,h=this.moduleCount-1;h>0;h-=2)for(6==h&&h--;;){for(var i=0;2>i;i++)if(null==this.modules[d][h-i]){var j=!1;g>>e));var k=f.getMask(b,d,h-i);k&&(j=!j),this.modules[d][h-i]=j,e--,-1==e&&(g++,e=7)}if(d+=c,0>d||this.moduleCount<=d){d-=c,c=-c;break}}}},b.PAD0=236,b.PAD1=17,b.createData=function(a,c,d){for(var e=j.getRSBlocks(a,c),g=new k,h=0;h8*l)throw new Error("code length overflow. ("+g.getLengthInBits()+">"+8*l+")");for(g.getLengthInBits()+4<=8*l&&g.put(0,4);0!=g.getLengthInBits()%8;)g.putBit(!1);for(;;){if(g.getLengthInBits()>=8*l)break;if(g.put(b.PAD0,8),g.getLengthInBits()>=8*l)break;g.put(b.PAD1,8)}return b.createBytes(g,e)},b.createBytes=function(a,b){for(var c=0,d=0,e=0,g=new Array(b.length),h=new Array(b.length),j=0;j=0?p.get(q):0}}for(var r=0,m=0;mm;m++)for(var j=0;jm;m++)for(var j=0;j=0;)b^=f.G15<=0;)b^=f.G18<>>=1;return b},getPatternPosition:function(a){return f.PATTERN_POSITION_TABLE[a-1]},getMask:function(a,b,c){switch(a){case e.PATTERN000:return 0==(b+c)%2;case e.PATTERN001:return 0==b%2;case e.PATTERN010:return 0==c%3;case e.PATTERN011:return 0==(b+c)%3;case e.PATTERN100:return 0==(Math.floor(b/2)+Math.floor(c/3))%2;case e.PATTERN101:return 0==b*c%2+b*c%3;case e.PATTERN110:return 0==(b*c%2+b*c%3)%2;case e.PATTERN111:return 0==(b*c%3+(b+c)%2)%2;default:throw new Error("bad maskPattern:"+a)}},getErrorCorrectPolynomial:function(a){for(var b=new i([1],0),c=0;a>c;c++)b=b.multiply(new i([1,g.gexp(c)],0));return b},getLengthInBits:function(a,b){if(b>=1&&10>b)switch(a){case c.MODE_NUMBER:return 10;case c.MODE_ALPHA_NUM:return 9;case c.MODE_8BIT_BYTE:return 8;case c.MODE_KANJI:return 8;default:throw new Error("mode:"+a)}else if(27>b)switch(a){case c.MODE_NUMBER:return 12;case c.MODE_ALPHA_NUM:return 11;case c.MODE_8BIT_BYTE:return 16;case c.MODE_KANJI:return 10;default:throw new Error("mode:"+a)}else{if(!(41>b))throw new Error("type:"+b);switch(a){case c.MODE_NUMBER:return 14;case c.MODE_ALPHA_NUM:return 13;case c.MODE_8BIT_BYTE:return 16;case c.MODE_KANJI:return 12;default:throw new Error("mode:"+a)}}},getLostPoint:function(a){for(var b=a.getModuleCount(),c=0,d=0;b>d;d++)for(var e=0;b>e;e++){for(var f=0,g=a.isDark(d,e),h=-1;1>=h;h++)if(!(0>d+h||d+h>=b))for(var i=-1;1>=i;i++)0>e+i||e+i>=b||(0!=h||0!=i)&&g==a.isDark(d+h,e+i)&&f++;f>5&&(c+=3+f-5)}for(var d=0;b-1>d;d++)for(var e=0;b-1>e;e++){var j=0;a.isDark(d,e)&&j++,a.isDark(d+1,e)&&j++,a.isDark(d,e+1)&&j++,a.isDark(d+1,e+1)&&j++,(0==j||4==j)&&(c+=3)}for(var d=0;b>d;d++)for(var e=0;b-6>e;e++)a.isDark(d,e)&&!a.isDark(d,e+1)&&a.isDark(d,e+2)&&a.isDark(d,e+3)&&a.isDark(d,e+4)&&!a.isDark(d,e+5)&&a.isDark(d,e+6)&&(c+=40);for(var e=0;b>e;e++)for(var d=0;b-6>d;d++)a.isDark(d,e)&&!a.isDark(d+1,e)&&a.isDark(d+2,e)&&a.isDark(d+3,e)&&a.isDark(d+4,e)&&!a.isDark(d+5,e)&&a.isDark(d+6,e)&&(c+=40);for(var k=0,e=0;b>e;e++)for(var d=0;b>d;d++)a.isDark(d,e)&&k++;var l=Math.abs(100*k/b/b-50)/5;return c+=10*l}},g={glog:function(a){if(1>a)throw new Error("glog("+a+")");return g.LOG_TABLE[a]},gexp:function(a){for(;0>a;)a+=255;for(;a>=256;)a-=255;return g.EXP_TABLE[a]},EXP_TABLE:new Array(256),LOG_TABLE:new Array(256)},h=0;8>h;h++)g.EXP_TABLE[h]=1<h;h++)g.EXP_TABLE[h]=g.EXP_TABLE[h-4]^g.EXP_TABLE[h-5]^g.EXP_TABLE[h-6]^g.EXP_TABLE[h-8];for(var h=0;255>h;h++)g.LOG_TABLE[g.EXP_TABLE[h]]=h;i.prototype={get:function(a){return this.num[a]},getLength:function(){return this.num.length},multiply:function(a){for(var b=new Array(this.getLength()+a.getLength()-1),c=0;cf;f++)for(var g=c[3*f+0],h=c[3*f+1],i=c[3*f+2],k=0;g>k;k++)e.push(new j(h,i));return e},j.getRsBlockTable=function(a,b){switch(b){case d.L:return j.RS_BLOCK_TABLE[4*(a-1)+0];case d.M:return j.RS_BLOCK_TABLE[4*(a-1)+1];case d.Q:return j.RS_BLOCK_TABLE[4*(a-1)+2];case d.H:return j.RS_BLOCK_TABLE[4*(a-1)+3];default:return void 0}},k.prototype={get:function(a){var b=Math.floor(a/8);return 1==(1&this.buffer[b]>>>7-a%8)},put:function(a,b){for(var c=0;b>c;c++)this.putBit(1==(1&a>>>b-c-1))},getLengthInBits:function(){return this.length},putBit:function(a){var b=Math.floor(this.length/8);this.buffer.length<=b&&this.buffer.push(0),a&&(this.buffer[b]|=128>>>this.length%8),this.length++}};var l=[[17,14,11,7],[32,26,20,14],[53,42,32,24],[78,62,46,34],[106,84,60,44],[134,106,74,58],[154,122,86,64],[192,152,108,84],[230,180,130,98],[271,213,151,119],[321,251,177,137],[367,287,203,155],[425,331,241,177],[458,362,258,194],[520,412,292,220],[586,450,322,250],[644,504,364,280],[718,560,394,310],[792,624,442,338],[858,666,482,382],[929,711,509,403],[1003,779,565,439],[1091,857,611,461],[1171,911,661,511],[1273,997,715,535],[1367,1059,751,593],[1465,1125,805,625],[1528,1190,868,658],[1628,1264,908,698],[1732,1370,982,742],[1840,1452,1030,790],[1952,1538,1112,842],[2068,1628,1168,898],[2188,1722,1228,958],[2303,1809,1283,983],[2431,1911,1351,1051],[2563,1989,1423,1093],[2699,2099,1499,1139],[2809,2213,1579,1219],[2953,2331,1663,1273]],o=function(){var a=function(a,b){this._el=a,this._htOption=b};return a.prototype.draw=function(a){function g(a,b){var c=document.createElementNS("http://www.w3.org/2000/svg",a);for(var d in b)b.hasOwnProperty(d)&&c.setAttribute(d,b[d]);return c}var b=this._htOption,c=this._el,d=a.getModuleCount();Math.floor(b.width/d),Math.floor(b.height/d),this.clear();var h=g("svg",{viewBox:"0 0 "+String(d)+" "+String(d),width:"100%",height:"100%",fill:b.colorLight});h.setAttributeNS("http://www.w3.org/2000/xmlns/","xmlns:xlink","http://www.w3.org/1999/xlink"),c.appendChild(h),h.appendChild(g("rect",{fill:b.colorDark,width:"1",height:"1",id:"template"}));for(var i=0;d>i;i++)for(var j=0;d>j;j++)if(a.isDark(i,j)){var k=g("use",{x:String(i),y:String(j)});k.setAttributeNS("http://www.w3.org/1999/xlink","href","#template"),h.appendChild(k)}},a.prototype.clear=function(){for(;this._el.hasChildNodes();)this._el.removeChild(this._el.lastChild)},a}(),p="svg"===document.documentElement.tagName.toLowerCase(),q=p?o:m()?function(){function a(){this._elImage.src=this._elCanvas.toDataURL("image/png"),this._elImage.style.display="block",this._elCanvas.style.display="none"}function d(a,b){var c=this;if(c._fFail=b,c._fSuccess=a,null===c._bSupportDataURI){var d=document.createElement("img"),e=function(){c._bSupportDataURI=!1,c._fFail&&_fFail.call(c)},f=function(){c._bSupportDataURI=!0,c._fSuccess&&c._fSuccess.call(c)};return d.onabort=e,d.onerror=e,d.onload=f,d.src="data:image/gif;base64,iVBORw0KGgoAAAANSUhEUgAAAAUAAAAFCAYAAACNbyblAAAAHElEQVQI12P4//8/w38GIAXDIBKE0DHxgljNBAAO9TXL0Y4OHwAAAABJRU5ErkJggg==",void 0}c._bSupportDataURI===!0&&c._fSuccess?c._fSuccess.call(c):c._bSupportDataURI===!1&&c._fFail&&c._fFail.call(c)}if(this._android&&this._android<=2.1){var b=1/window.devicePixelRatio,c=CanvasRenderingContext2D.prototype.drawImage;CanvasRenderingContext2D.prototype.drawImage=function(a,d,e,f,g,h,i,j){if("nodeName"in a&&/img/i.test(a.nodeName))for(var l=arguments.length-1;l>=1;l--)arguments[l]=arguments[l]*b;else"undefined"==typeof j&&(arguments[1]*=b,arguments[2]*=b,arguments[3]*=b,arguments[4]*=b);c.apply(this,arguments)}}var e=function(a,b){this._bIsPainted=!1,this._android=n(),this._htOption=b,this._elCanvas=document.createElement("canvas"),this._elCanvas.width=b.width,this._elCanvas.height=b.height,a.appendChild(this._elCanvas),this._el=a,this._oContext=this._elCanvas.getContext("2d"),this._bIsPainted=!1,this._elImage=document.createElement("img"),this._elImage.style.display="none",this._el.appendChild(this._elImage),this._bSupportDataURI=null};return e.prototype.draw=function(a){var b=this._elImage,c=this._oContext,d=this._htOption,e=a.getModuleCount(),f=d.width/e,g=d.height/e,h=Math.round(f),i=Math.round(g);b.style.display="none",this.clear();for(var j=0;e>j;j++)for(var k=0;e>k;k++){var l=a.isDark(j,k),m=k*f,n=j*g;c.strokeStyle=l?d.colorDark:d.colorLight,c.lineWidth=1,c.fillStyle=l?d.colorDark:d.colorLight,c.fillRect(m,n,f,g),c.strokeRect(Math.floor(m)+.5,Math.floor(n)+.5,h,i),c.strokeRect(Math.ceil(m)-.5,Math.ceil(n)-.5,h,i)}this._bIsPainted=!0},e.prototype.makeImage=function(){this._bIsPainted&&d.call(this,a)},e.prototype.isPainted=function(){return this._bIsPainted},e.prototype.clear=function(){this._oContext.clearRect(0,0,this._elCanvas.width,this._elCanvas.height),this._bIsPainted=!1},e.prototype.round=function(a){return a?Math.floor(1e3*a)/1e3:a},e}():function(){var a=function(a,b){this._el=a,this._htOption=b};return a.prototype.draw=function(a){for(var b=this._htOption,c=this._el,d=a.getModuleCount(),e=Math.floor(b.width/d),f=Math.floor(b.height/d),g=[''],h=0;d>h;h++){g.push("");for(var i=0;d>i;i++)g.push(' ');g.push(" ")}g.push("
"),c.innerHTML=g.join("");var j=c.childNodes[0],k=(b.width-j.offsetWidth)/2,l=(b.height-j.offsetHeight)/2;k>0&&l>0&&(j.style.margin=l+"px "+k+"px")},a.prototype.clear=function(){this._el.innerHTML=""},a}();QRCode=function(a,b){if(this._htOption={width:256,height:256,typeNumber:4,colorDark:"#000000",colorLight:"#ffffff",correctLevel:d.H},"string"==typeof b&&(b={text:b}),b)for(var c in b)this._htOption[c]=b[c];"string"==typeof a&&(a=document.getElementById(a)),this._android=n(),this._el=a,this._oQRCode=null,this._oDrawing=new q(this._el,this._htOption),this._htOption.text&&this.makeCode(this._htOption.text)},QRCode.prototype.makeCode=function(a){this._oQRCode=new b(r(a,this._htOption.correctLevel),this._htOption.correctLevel),this._oQRCode.addData(a),this._oQRCode.make(),this._el.title=a,this._oDrawing.draw(this._oQRCode),this.makeImage()},QRCode.prototype.makeImage=function(){"function"==typeof this._oDrawing.makeImage&&(!this._android||this._android>=3)&&this._oDrawing.makeImage()},QRCode.prototype.clear=function(){this._oDrawing.clear()},QRCode.CorrectLevel=d}();
--------------------------------------------------------------------------------
/inst/rmarkdown/templates/betterposter/skeleton/skeleton.Rmd:
--------------------------------------------------------------------------------
1 | ---
2 | title: >
3 | Another Better Scientific Poster Using R Markdown and pagedown
4 | author:
5 | - name: Garrick Aden-Buie
6 | affiliation: 1
7 | extra:
8 | - "garrick@adenbuie.com"
9 | - "@grrrck"
10 | - name: Mike Morrison
11 | affiliation: 2
12 | - name: Brent Thorne
13 | affiliation: 3
14 | - name: Yihui Xie
15 | affiliation: 4
16 | affiliation:
17 | - Gerke Lab, Moffitt Cancer Center, Tampa, FL
18 | - Michigan State University
19 | - Author and maintainer of [posterdown](https://github.com/brentthorne/posterdown)
20 | - Author of [pagedown](https://github.com/rstudio/pagedown) and much, much more!
21 | date: "`r Sys.Date()`"
22 | output:
23 | betterposter::poster_better:
24 | # Optional styling arguments
25 | hero_background: "#0F5D4F"
26 | accent_color: "#444444"
27 | hero_color: "#FFFFFF"
28 | logo: "http://bit.ly/2UFWcbr"
29 | # See betterposter::qrcode_options() for help
30 | qrcode:
31 | text: "https://github.com/gadenbuie/betterposter"
32 | size: "350"
33 | mathjax: false
34 | # Generic rmarkdown arguments
35 | highlight: tango
36 | self_contained: true
37 | references:
38 | - id: fenner2012a
39 | title: One-click science marketing
40 | author:
41 | - family: Fenner
42 | given: Martin
43 | container-title: Nature Materials
44 | volume: 11
45 | URL: 'http://dx.doi.org/10.1038/nmat3283'
46 | DOI: 10.1038/nmat3283
47 | issue: 4
48 | publisher: Nature Publishing Group
49 | page: 261-263
50 | type: article-journal
51 | issued:
52 | year: 2012
53 | month: 3
54 | ---
55 |
56 | ```{css echo=FALSE}
57 | /* Adjust space at top of #hero (center panel) */
58 | #hero {
59 | padding-top: 33%;
60 | }
61 | ```
62 |
63 |
64 |
65 |
71 |
72 | # **Main finding** goes here, translated into **plain english**. **Emphasize** the important words.
73 |
74 | *Additional text and content can be added here if you really want.*
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 | ## Abstract
85 |
86 | In recent years, much research has been devoted to the emulation of DHCP; on the other hand, few have explored the construction of journaling file systems.
87 | The inability to effect complexity theory of this has been encouraging. The notion that cryptographers synchronize with game-theoretic configurations is largely adamantly opposed [@fenner2012a].
88 |
89 |
90 | ## Methods
91 |
92 | 1. IPv6 can be made autonomous, concurrent, and client-server
93 |
94 | 2. 7-month-long trace showing that our design is feasible
95 |
96 | 3. Suffix trees and the Ethernet are entirely incompatible.
97 |
98 | 4. Model for our methodology:
99 | - fiber-optic cables
100 | - simulated annealing
101 | - superblocks
102 | - multicast algorithms
103 |
104 | ## Implementation
105 |
106 | After several days of difficult implementing, we finally have a working implementation of our heuristic.
107 | BEVY is composed of a **hacked operating system**, a codebase of **61** Lisp files, and a **hand-optimized compiler**.
108 |
109 | 
110 |
111 | ## Evaluation
112 |
113 | Is it possible to justify having paid little attention to our implementation and experimental setup?
114 | Yes, but only in theory.
115 |
116 | We ran four novel experiments:
117 |
118 | 1. Deployed 35 Macintosh SEs underwater and compared our suffix trees accordingly
119 | 2. Compared effective time since 1967 on the Sprite, L4 and Multics operating systems
120 | 3. Measured _tape drive throughput_ as a function of _hard disk space_ on an `Apple ][`
121 | 4. Deployed 36 `Apple ][`es across the 100-node network and tested again
122 |
123 | ## Results
124 |
125 | In conclusion, in our research we described **BEVY**, a novel heuristic for the analysis of link-level acknowledgements.
126 | We proved that simplicity in our heuristic is not a question.
127 | Our framework for developing the analysis of thin clients is famously excellent.
128 |
129 | This text brought to you by [SCIgen](https://pdos.csail.mit.edu/archive/scigen/), an Automatic CS Paper Generator.
130 |
131 |
132 |
133 |
134 |
135 |
136 |
137 |
138 | # Extra Tables & Figures
139 |
140 | ## Cars are fast
141 |
142 | ```{r eval=TRUE, echo=TRUE, warning=FALSE, message=FALSE}
143 | library(dplyr)
144 | library(ggplot2)
145 |
146 | mtcars %>%
147 | skimr::skim_to_wide() %>%
148 | select(variable, n, mean, sd, p0, p50, p100) %>%
149 | knitr::kable(format = "html")
150 | ```
151 |
152 | ## Diamonds are foreveer
153 |
154 | ```{r, fig.width=6, fig.height = 3, out.width="100%"}
155 | ggplot(diamonds) +
156 | aes(clarity, price) +
157 | geom_point()
158 | ```
159 |
160 | ## Starwars has characters
161 |
162 | ```{r echo=TRUE}
163 | starwars %>%
164 | mutate(n_films = sapply(films, length)) %>%
165 | select(name, hair_color, height, species, n_films) %>%
166 | arrange(desc(n_films)) %>%
167 | head(10) %>%
168 | knitr::kable(caption = paste(
169 | "Characters with most",
170 | "appearances in Star Wars movies."))
171 | ```
172 |
173 | ## Heavy cars are inefficient
174 |
175 | ```{r, fig.width=6, fig.height = 3, out.width="100%"}
176 | ggplot(mtcars) +
177 | aes(wt, mpg) +
178 | geom_smooth(method = "lm") +
179 | geom_point() +
180 | labs(title = "Something something cars",
181 | subtitle = "A boring regression",
182 | caption = "Source: {mtcars} of course",
183 | x = "Weight of the car",
184 | y = "Fuel efficiency (mpg)")
185 | ```
186 |
187 |
188 |
189 | # References
190 |
--------------------------------------------------------------------------------
/inst/rmarkdown/templates/betterposter/template.yaml:
--------------------------------------------------------------------------------
1 | name: HTML Better Poster
2 | description: >
3 | Create a poster in HTML with the Better Poster style.
4 | create_dir: FALSE
5 |
--------------------------------------------------------------------------------
/man/figures/betterposter-example.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/GerkeLab/betterposter/f14d1432116ceb8c709e4ecccae06c36c88c2788/man/figures/betterposter-example.png
--------------------------------------------------------------------------------
/man/poster_better.Rd:
--------------------------------------------------------------------------------
1 | % Generated by roxygen2: do not edit by hand
2 | % Please edit documentation in R/betterposter.R
3 | \name{poster_better}
4 | \alias{poster_better}
5 | \title{Create a Better Poster in HTML}
6 | \usage{
7 | poster_better(..., css = NULL, hero_background = NULL,
8 | hero_color = NULL, qrcode = NULL, logo = NULL,
9 | accent_color = NULL, mathjax = FALSE, pandoc_args = NULL)
10 | }
11 | \value{
12 | An R Markdown output format.
13 | }
14 | \description{
15 | Create a Better Poster in HTML
16 | }
17 |
--------------------------------------------------------------------------------