Add build system for static assets
This commit is contained in:
parent
ab5427dca2
commit
4b4749d3bf
13 changed files with 3426 additions and 70 deletions
3
.gitignore
vendored
3
.gitignore
vendored
|
@ -1,4 +1,5 @@
|
|||
htmlroc.exe
|
||||
htmlroc
|
||||
out.html
|
||||
rules.txt
|
||||
rules.txt
|
||||
node_modules
|
||||
|
|
11
README.md
11
README.md
|
@ -9,6 +9,7 @@ Converts MLP:CCG rule files from text to HTML!
|
|||
- Go 1.12+
|
||||
- The text rules from Hithroc's site:
|
||||
https://horse.cards/rules/latest.txt
|
||||
- Node.js **(optional)**
|
||||
|
||||
### Running htmlroc
|
||||
|
||||
|
@ -21,6 +22,16 @@ Converts MLP:CCG rule files from text to HTML!
|
|||
|
||||
Alternately, you can compile with `go install` and use the command line flags to specify location of `rules.txt` and `template.html`
|
||||
|
||||
### Rebuilding static assets
|
||||
|
||||
If you have node.js installed, you can also modify the static assets and rebuild them. Source files are in `static-src`. To rebuild, run either `npm i` or `yarn install` depending on your package manager of choice and then:
|
||||
|
||||
```
|
||||
yarn build
|
||||
```
|
||||
|
||||
This will build the CSS/JS files needed for the provided template.
|
||||
|
||||
## Thanks to
|
||||
|
||||
- [Hithroc](https://hithroc.org/) for maitaining text versions of the rules
|
||||
|
|
17
gulpfile.js
Normal file
17
gulpfile.js
Normal file
|
@ -0,0 +1,17 @@
|
|||
const { src, dest, parallel } = require("gulp");
|
||||
const sass = require("gulp-sass");
|
||||
const sourcemaps = require("gulp-sourcemaps");
|
||||
const concat = require("gulp-concat");
|
||||
|
||||
sass.compiler = require("dart-sass");
|
||||
|
||||
function css() {
|
||||
return src("static-src/**/*.scss")
|
||||
.pipe(sourcemaps.init())
|
||||
.pipe(sass({ outputStyle: "compressed" }).on("error", sass.logError))
|
||||
.pipe(concat("style.min.css"))
|
||||
.pipe(sourcemaps.write("map"))
|
||||
.pipe(dest("static"));
|
||||
}
|
||||
|
||||
exports.default = parallel(css);
|
12
main.go
12
main.go
|
@ -140,6 +140,16 @@ func main() {
|
|||
default:
|
||||
// If there is at least a rule, assume it's a continuation of the last rule
|
||||
if len(currentSection.Rules) > 0 {
|
||||
// HACK FOR 212
|
||||
// Rule 212 is missing "(212.1)" before the rule text
|
||||
if currentSection.Rules[len(currentSection.Rules)-1].ID == "212" {
|
||||
currentSection.Rules = append(currentSection.Rules, TemplateRule{
|
||||
ID: "212.1",
|
||||
Text: trimmed,
|
||||
Depth: depth,
|
||||
})
|
||||
break
|
||||
}
|
||||
currentSection.Rules[len(currentSection.Rules)-1].Text += "\n" + line
|
||||
} else {
|
||||
// No rules? Might be an extra
|
||||
|
@ -164,4 +174,4 @@ func checkErr(err error, fmtstr string, args ...interface{}) {
|
|||
fmt.Fprintln(os.Stderr, err.Error())
|
||||
os.Exit(1)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
12
package.json
Normal file
12
package.json
Normal file
|
@ -0,0 +1,12 @@
|
|||
{
|
||||
"dependencies": {
|
||||
"dart-sass": "^1.21.0",
|
||||
"gulp": "^4.0.2",
|
||||
"gulp-concat": "^2.6.1",
|
||||
"gulp-sass": "^4.0.2",
|
||||
"gulp-sourcemaps": "^2.6.5"
|
||||
},
|
||||
"scripts": {
|
||||
"build": "gulp"
|
||||
}
|
||||
}
|
87
static-src/stylesheets/default.scss
Normal file
87
static-src/stylesheets/default.scss
Normal file
|
@ -0,0 +1,87 @@
|
|||
@import url("https://fonts.googleapis.com/css?family=Roboto:300,400,500&display=swap");
|
||||
|
||||
body {
|
||||
font-family: "Roboto", sans-serif;
|
||||
font-weight: 300;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
font-size: 11pt;
|
||||
line-height: 160%;
|
||||
}
|
||||
|
||||
main {
|
||||
flex: 1;
|
||||
max-width: 800px;
|
||||
}
|
||||
|
||||
h1,
|
||||
h2 {
|
||||
color: #4b5b69;
|
||||
font-weight: 400;
|
||||
}
|
||||
|
||||
p {
|
||||
margin: 0;
|
||||
padding: 2pt 0;
|
||||
}
|
||||
|
||||
.rules {
|
||||
ul {
|
||||
padding-left: 10pt;
|
||||
}
|
||||
li {
|
||||
margin: 10pt 0;
|
||||
list-style-type: none;
|
||||
}
|
||||
|
||||
.depth-0 {
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
.depth-2 {
|
||||
padding-left: 20pt;
|
||||
}
|
||||
|
||||
.depth-4 {
|
||||
padding-left: 40pt;
|
||||
}
|
||||
|
||||
.depth-6 {
|
||||
padding-left: 60pt;
|
||||
}
|
||||
}
|
||||
|
||||
.glossary {
|
||||
dt {
|
||||
font-weight: 500;
|
||||
}
|
||||
dd {
|
||||
margin-inline-start: 10pt;
|
||||
margin-bottom: 1rem;
|
||||
}
|
||||
}
|
||||
|
||||
.toc {
|
||||
ul {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
flex-wrap: wrap;
|
||||
max-height: 700pt;
|
||||
}
|
||||
|
||||
& > ul > li {
|
||||
margin-bottom: 1rem;
|
||||
}
|
||||
|
||||
a {
|
||||
color: #0d85ce;
|
||||
text-decoration: none;
|
||||
|
||||
&:hover {
|
||||
color: #87c7ff;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@media (min-width: 960px) {
|
||||
}
|
1
static/map/style.min.css.map
Normal file
1
static/map/style.min.css.map
Normal file
|
@ -0,0 +1 @@
|
|||
{"version":3,"sources":["stylesheets/default.scss"],"names":[],"mappings":"AAAQ,iFAER,KACC,gCACA,gBACA,aACA,uBACA,eACA,iBAGD,KACC,OACA,gBAGD,MAEC,cACA,gBAGD,EACC,SACA,cAIA,UACC,kBAED,UACC,cACA,qBAGD,gBACC,gBAGD,gBACC,kBAGD,gBACC,kBAGD,gBACC,kBAKD,aACC,gBAED,aACC,yBACA,mBAKD,QACC,aACA,sBACA,eACA,iBAGD,WACC,mBAGD,OACC,cACA,qBAEA,aACC","file":"../style.min.css","sourcesContent":["@import url(\"https://fonts.googleapis.com/css?family=Roboto:300,400,500&display=swap\");\r\n\r\nbody {\r\n\tfont-family: \"Roboto\", sans-serif;\r\n\tfont-weight: 300;\r\n\tdisplay: flex;\r\n\tjustify-content: center;\r\n\tfont-size: 11pt;\r\n\tline-height: 160%;\r\n}\r\n\r\nmain {\r\n\tflex: 1;\r\n\tmax-width: 800px;\r\n}\r\n\r\nh1,\r\nh2 {\r\n\tcolor: #4b5b69;\r\n\tfont-weight: 400;\r\n}\r\n\r\np {\r\n\tmargin: 0;\r\n\tpadding: 2pt 0;\r\n}\r\n\r\n.rules {\r\n\tul {\r\n\t\tpadding-left: 10pt;\r\n\t}\r\n\tli {\r\n\t\tmargin: 10pt 0;\r\n\t\tlist-style-type: none;\r\n\t}\r\n\r\n\t.depth-0 {\r\n\t\tfont-weight: 500;\r\n\t}\r\n\r\n\t.depth-2 {\r\n\t\tpadding-left: 20pt;\r\n\t}\r\n\r\n\t.depth-4 {\r\n\t\tpadding-left: 40pt;\r\n\t}\r\n\r\n\t.depth-6 {\r\n\t\tpadding-left: 60pt;\r\n\t}\r\n}\r\n\r\n.glossary {\r\n\tdt {\r\n\t\tfont-weight: 500;\r\n\t}\r\n\tdd {\r\n\t\tmargin-inline-start: 10pt;\r\n\t\tmargin-bottom: 1rem;\r\n\t}\r\n}\r\n\r\n.toc {\r\n\tul {\r\n\t\tdisplay: flex;\r\n\t\tflex-direction: column;\r\n\t\tflex-wrap: wrap;\r\n\t\tmax-height: 700pt;\r\n\t}\r\n\r\n\t& > ul > li {\r\n\t\tmargin-bottom: 1rem;\r\n\t}\r\n\r\n\ta {\r\n\t\tcolor: #0d85ce;\r\n\t\ttext-decoration: none;\r\n\r\n\t\t&:hover {\r\n\t\t\tcolor: #87c7ff;\r\n\t\t}\r\n\t}\r\n}\r\n\r\n@media (min-width: 960px) {\r\n}\r\n"]}
|
0
static/script.js → static/script.min.js
vendored
0
static/script.js → static/script.min.js
vendored
|
@ -1,60 +0,0 @@
|
|||
@import url("https://fonts.googleapis.com/css?family=Roboto:300,400,500&display=swap");
|
||||
|
||||
body {
|
||||
font-family: "Roboto", sans-serif;
|
||||
font-weight: 300;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
font-size: 11pt;
|
||||
line-height: 150%;
|
||||
}
|
||||
|
||||
main {
|
||||
flex: 1;
|
||||
max-width: 60em;
|
||||
}
|
||||
|
||||
h1,
|
||||
h2 {
|
||||
color: #4b5b69;
|
||||
font-weight: 400;
|
||||
}
|
||||
|
||||
p {
|
||||
margin: 0;
|
||||
padding: 2pt 0;
|
||||
}
|
||||
|
||||
ul {
|
||||
padding-left: 10pt;
|
||||
}
|
||||
|
||||
li {
|
||||
margin: 10pt 0;
|
||||
list-style-type: none;
|
||||
}
|
||||
|
||||
.depth-0 {
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
.depth-2 {
|
||||
padding-left: 20pt;
|
||||
}
|
||||
|
||||
.depth-4 {
|
||||
padding-left: 40pt;
|
||||
}
|
||||
|
||||
.depth-6 {
|
||||
padding-left: 60pt;
|
||||
}
|
||||
|
||||
.glossary dt {
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
.glossary dd {
|
||||
margin-inline-start: 10pt;
|
||||
margin-bottom: 1rem;
|
||||
}
|
2
static/style.min.css
vendored
Normal file
2
static/style.min.css
vendored
Normal file
|
@ -0,0 +1,2 @@
|
|||
@import"https://fonts.googleapis.com/css?family=Roboto:300,400,500&display=swap";body{font-family:"Roboto",sans-serif;font-weight:300;display:flex;justify-content:center;font-size:11pt;line-height:160%}main{flex:1;max-width:800px}h1,h2{color:#4b5b69;font-weight:400}p{margin:0;padding:2pt 0}.rules ul{padding-left:10pt}.rules li{margin:10pt 0;list-style-type:none}.rules .depth-0{font-weight:500}.rules .depth-2{padding-left:20pt}.rules .depth-4{padding-left:40pt}.rules .depth-6{padding-left:60pt}.glossary dt{font-weight:500}.glossary dd{margin-inline-start:10pt;margin-bottom:1rem}.toc ul{display:flex;flex-direction:column;flex-wrap:wrap;max-height:700pt}.toc>ul>li{margin-bottom:1rem}.toc a{color:#0d85ce;text-decoration:none}.toc a:hover{color:#87c7ff}
|
||||
/*# sourceMappingURL=map/style.min.css.map */
|
13
template.go
13
template.go
|
@ -9,6 +9,7 @@ var funmap = template.FuncMap{
|
|||
"toCredits": tplToCredits,
|
||||
"htmlify": tplHtmlify,
|
||||
"toGlossary": tplToGlossary,
|
||||
"firstLine": tplFirstLine,
|
||||
}
|
||||
|
||||
func tplToCredits(str string) template.HTML {
|
||||
|
@ -23,11 +24,19 @@ func tplToCredits(str string) template.HTML {
|
|||
}
|
||||
|
||||
func tplHtmlify(str string) template.HTML {
|
||||
// Replace newlines with <br />
|
||||
str = strings.ReplaceAll(str, "\n", "<br />")
|
||||
// Replace newlines with paragraph blocks
|
||||
str = strings.ReplaceAll(str, "\n", "</p><p>")
|
||||
return template.HTML(str)
|
||||
}
|
||||
|
||||
func tplFirstLine(str string) string {
|
||||
newline := strings.IndexRune(str, '\n')
|
||||
if newline < 0 {
|
||||
return str
|
||||
}
|
||||
return str[:newline]
|
||||
}
|
||||
|
||||
type glossaryEntry struct {
|
||||
Keyword string
|
||||
Definition string
|
||||
|
|
|
@ -3,17 +3,35 @@
|
|||
|
||||
<head>
|
||||
<title>{{ .Title }}</title>
|
||||
<link rel="stylesheet" href="static/style.css">
|
||||
<script src="static/script.js" defer></script>
|
||||
<link rel="stylesheet" href="static/style.min.css">
|
||||
<script src="static/script.min.js" defer></script>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<nav class="topbar">
|
||||
</nav>
|
||||
<nav class="topbar"></nav>
|
||||
<main>
|
||||
<header class="credits">
|
||||
{{ .Credits | toCredits }}
|
||||
</header>
|
||||
<section class="toc">
|
||||
<h2>Table of contents</h2>
|
||||
<ul>
|
||||
{{ range .Sections }}
|
||||
<li>
|
||||
<a href="#{{ .ID }}">{{ .ID }}. {{ .Title }}</a>
|
||||
<ul>
|
||||
{{ range .Rules }}
|
||||
{{ if (eq .Depth 0) }}
|
||||
<li>
|
||||
<a href="#{{ .ID }}">{{ .ID }}. {{ .Text | firstLine }}</a>
|
||||
</li>
|
||||
{{ end }}
|
||||
{{ end }}
|
||||
</ul>
|
||||
</li>
|
||||
{{ end }}
|
||||
</ul>
|
||||
</section>
|
||||
<section class="rules">
|
||||
{{ range .Sections }}
|
||||
<h2 id="{{ .ID }}">{{ .ID }}. {{ .Title }}</h2>
|
||||
|
@ -26,12 +44,14 @@
|
|||
{{ end }}
|
||||
</dl>
|
||||
{{ else }}
|
||||
{{ .Text | htmlify }}
|
||||
<p>{{ .Text | htmlify }}</p>
|
||||
{{ end }}
|
||||
{{ else }}
|
||||
<ul>
|
||||
{{ range .Rules }}
|
||||
<li id="{{ .ID }}" class="depth-{{ .Depth }}">({{ .ID }}) {{ .Text | htmlify }}</li>
|
||||
<li id="{{ .ID }}" class="depth-{{ .Depth }}">
|
||||
<p>({{ .ID }}) {{ .Text | htmlify }}</p>
|
||||
</li>
|
||||
{{ end }}
|
||||
</ul>
|
||||
{{ end }}
|
||||
|
|
Loading…
Reference in a new issue