Better edu home page
This commit is contained in:
parent
4e44ba0b45
commit
48af5e650d
Binary file not shown.
After Width: | Height: | Size: 103 KiB |
Binary file not shown.
After Width: | Height: | Size: 91 KiB |
Binary file not shown.
After Width: | Height: | Size: 106 KiB |
|
@ -7394,7 +7394,7 @@ article code {
|
|||
border-color: #aaa;
|
||||
border-color: var(--theme-color-dim); }
|
||||
|
||||
.c--dimmer, footer .list li:not(:last-child)::after {
|
||||
.c--dimmer, footer .list li:not(:last-child)::after, .edu-course .edu-article.coming-soon {
|
||||
color: #999;
|
||||
color: var(--dimmer-color); }
|
||||
|
||||
|
@ -8306,6 +8306,27 @@ nav.timecodes {
|
|||
text-align: center;
|
||||
margin: 10px 0; }
|
||||
|
||||
.edu-course .edu-article.coming-soon {
|
||||
font-style: italic; }
|
||||
|
||||
.edu-course .edu-article::after {
|
||||
content: '';
|
||||
position: absolute;
|
||||
width: 1rem;
|
||||
height: 10rem;
|
||||
border-width: 0 0 1px 1px;
|
||||
border-style: solid;
|
||||
border-color: #bbb;
|
||||
border-color: var(--dimmest-color);
|
||||
left: -1.5rem;
|
||||
top: -9rem;
|
||||
border-bottom-left-radius: 0.5rem; }
|
||||
|
||||
.edu-topic img {
|
||||
width: 100%;
|
||||
height: 14rem;
|
||||
object-fit: cover; }
|
||||
|
||||
.edu-article .note {
|
||||
color: red; }
|
||||
|
||||
|
|
|
@ -1,3 +1,32 @@
|
|||
.edu-course {
|
||||
.edu-article.coming-soon {
|
||||
@extend .c--dimmer;
|
||||
font-style: italic;
|
||||
}
|
||||
|
||||
.edu-article::after {
|
||||
$height: 10rem;
|
||||
content: '';
|
||||
position: absolute;
|
||||
width: 1rem;
|
||||
height: $height;
|
||||
border-width: 0 0 1px 1px;
|
||||
border-style: solid;
|
||||
@include usevar(border-color, dimmest-color);
|
||||
left: -1.5rem;
|
||||
top: 1rem - $height;
|
||||
border-bottom-left-radius: 0.5rem;
|
||||
}
|
||||
}
|
||||
|
||||
.edu-topic {
|
||||
img {
|
||||
width: 100%;
|
||||
height: 14rem;
|
||||
object-fit: cover;
|
||||
}
|
||||
}
|
||||
|
||||
.edu-article {
|
||||
.note {
|
||||
color: red;
|
||||
|
|
|
@ -41,7 +41,7 @@
|
|||
{{ end }}
|
||||
|
||||
{{ define "content" }}
|
||||
<div class="ph2 ph0-ns">
|
||||
<div class="ph3 ph0-ns">
|
||||
<h1>{{ .Title }}</h1>
|
||||
{{ if and .User .User.IsEduAuthor }}
|
||||
<div class="mb3">
|
||||
|
|
|
@ -1,28 +1,44 @@
|
|||
{{ template "base.html" . }}
|
||||
|
||||
{{ define "content" }}
|
||||
<div class="ph3 ph0-ns">
|
||||
<h1>Learn the Handmade way.</h1>
|
||||
|
||||
<h2>Guides</h2>
|
||||
<p>Dive into one of these topics and start learning.</p>
|
||||
|
||||
{{ if and .User .User.IsEduAuthor }}
|
||||
<div class="mb2">
|
||||
<a href="{{ .NewArticleUrl }}"><span class="big pr1">+</span> New Article</a>
|
||||
</div>
|
||||
{{ end }}
|
||||
|
||||
<div class="flex flex-column g3 mb3">
|
||||
{{ range .Articles }}
|
||||
<a class="c--inherit flex flex-column pa3 bg--dim br2" href="{{ .Url }}" >
|
||||
<h3 class="mb1 link">{{ .Title }}</h3>
|
||||
<div>{{ .Description }}</div>
|
||||
</a>
|
||||
{{ end }}
|
||||
<div class="flex flex-column flex-row-ns g3 mt3 mb4">
|
||||
<a href="#compilers" class="edu-topic db flex-fair-ns bg--dim br3 overflow-hidden c--inherit flex flex-column">
|
||||
<img src="{{ static "education/compilers.jpg" }}">
|
||||
<div class="pa3">
|
||||
<h2>Compilers</h2>
|
||||
<div>
|
||||
Learn how programming languages are made.
|
||||
</div>
|
||||
</div>
|
||||
</a>
|
||||
<a href="#networking" class="edu-topic db flex-fair-ns bg--dim br3 overflow-hidden c--inherit flex flex-column">
|
||||
<img src="{{ static "education/networking.jpg" }}">
|
||||
<div class="pa3">
|
||||
<h2>Networking</h2>
|
||||
<div>
|
||||
Learn how computers communicate, and how the internet actually works.
|
||||
</div>
|
||||
</div>
|
||||
</a>
|
||||
<a href="#time" class="edu-topic db flex-fair-ns bg--dim br3 overflow-hidden c--inherit flex flex-column">
|
||||
<img src="{{ static "education/time.jpg" }}">
|
||||
<div class="pa3">
|
||||
<h2>Time</h2>
|
||||
<div>
|
||||
Get better at handling time, from calendars to timezones to clock sync.
|
||||
</div>
|
||||
</div>
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<h2>What makes us different?</h2>
|
||||
|
||||
<div class="flex flex-column flex-row-ns g3">
|
||||
<div class="flex flex-column flex-row-ns g3 mb4">
|
||||
<div class="flex-fair bg--dim pa3 br2">
|
||||
<h3>Real material.</h3>
|
||||
|
||||
|
@ -40,10 +56,34 @@
|
|||
</div>
|
||||
</div>
|
||||
|
||||
{{ if and .User .User.IsEduAuthor }}
|
||||
<div class="mt3">
|
||||
<b>SECRET AUTHOR MAINTENANCE COMMANDS:</b>
|
||||
<a href="{{ .RerenderUrl }}">Rerender all content</a>
|
||||
<h2>All Topics</h2>
|
||||
|
||||
{{ range .Courses }}
|
||||
<div id="{{ .Slug }}" class="edu-course mv3 bg--dim pa3 br3">
|
||||
<h3>{{ .Name }}</h3>
|
||||
<div class="overflow-hidden">
|
||||
<div class="edu-articles ml3 pl3">
|
||||
{{ range .Articles }}
|
||||
<div class="edu-article mt3 relative {{ if not .Published }}coming-soon{{ end }}">
|
||||
{{ if or (and $.User $.User.IsEduTester) .Published }}
|
||||
<a href="{{ .Url }}"><h4>{{ .Title }}</h4></a>
|
||||
{{ else }}
|
||||
<h4>{{ .Title }} (coming soon)</h4>
|
||||
{{ end }}
|
||||
<div>{{ .Description }}</div>
|
||||
</div>
|
||||
{{ end }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{{ end }}
|
||||
|
||||
{{ if and .User .User.IsEduAuthor }}
|
||||
<div class="mt3">
|
||||
<b>SECRET AUTHOR COMMANDS:</b>
|
||||
<div><a href="{{ .RerenderUrl }}">Rerender all content</a></div>
|
||||
<div><a href="{{ .NewArticleUrl }}"><span class="big pr1">+</span> New Article</a></div>
|
||||
</div>
|
||||
{{ end }}
|
||||
</div>
|
||||
{{ end }}
|
||||
|
|
|
@ -395,6 +395,12 @@ type TextEditor struct {
|
|||
UploadUrl string
|
||||
}
|
||||
|
||||
type EduCourse struct {
|
||||
Name string
|
||||
Slug string
|
||||
Articles []EduArticle
|
||||
}
|
||||
|
||||
type EduArticle struct {
|
||||
Title string
|
||||
Slug string
|
||||
|
|
|
@ -23,24 +23,68 @@ import (
|
|||
func EducationIndex(c *RequestContext) ResponseData {
|
||||
type indexData struct {
|
||||
templates.BaseData
|
||||
Articles []templates.EduArticle
|
||||
Courses []templates.EduCourse
|
||||
NewArticleUrl string
|
||||
RerenderUrl string
|
||||
}
|
||||
|
||||
articles, err := fetchEduArticles(c, c.Conn, models.EduArticleTypeArticle, c.CurrentUser)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
// TODO: Someday this can be dynamic again? Maybe? Or not? Who knows??
|
||||
// articles, err := fetchEduArticles(c, c.Conn, models.EduArticleTypeArticle, c.CurrentUser)
|
||||
// if err != nil {
|
||||
// panic(err)
|
||||
// }
|
||||
|
||||
var tmplArticles []templates.EduArticle
|
||||
for _, article := range articles {
|
||||
tmplArticles = append(tmplArticles, templates.EducationArticleToTemplate(&article))
|
||||
// var tmplArticles []templates.EduArticle
|
||||
// for _, article := range articles {
|
||||
// tmplArticles = append(tmplArticles, templates.EducationArticleToTemplate(&article))
|
||||
// }
|
||||
|
||||
article := func(slug string) templates.EduArticle {
|
||||
if article, err := fetchEduArticle(c, c.Conn, slug, models.EduArticleTypeArticle, c.CurrentUser); err == nil {
|
||||
return templates.EducationArticleToTemplate(article)
|
||||
} else if errors.Is(err, db.NotFound) {
|
||||
return templates.EduArticle{
|
||||
Title: "<UNKNOWN ARTICLE>",
|
||||
}
|
||||
} else {
|
||||
panic(err)
|
||||
}
|
||||
}
|
||||
|
||||
tmpl := indexData{
|
||||
BaseData: getBaseData(c, "Handmade Education", nil),
|
||||
Articles: tmplArticles,
|
||||
BaseData: getBaseData(c, "Handmade Education", nil),
|
||||
Courses: []templates.EduCourse{
|
||||
{
|
||||
Name: "Compilers",
|
||||
Slug: "compilers",
|
||||
Articles: []templates.EduArticle{
|
||||
article("compilers"),
|
||||
{
|
||||
Title: "Baby's first language theory",
|
||||
Description: "State machines, abstract datatypes, type theory...",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
Name: "Networking",
|
||||
Slug: "networking",
|
||||
Articles: []templates.EduArticle{
|
||||
article("networking"),
|
||||
{
|
||||
Title: "Internet infrastructure",
|
||||
Description: "How does the internet actually work? How does your ISP know where to send your data? What happens to the internet if physical communication breaks down?",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
Name: "Time",
|
||||
Slug: "time",
|
||||
Articles: []templates.EduArticle{
|
||||
article("time"),
|
||||
article("ntp"),
|
||||
},
|
||||
},
|
||||
},
|
||||
NewArticleUrl: hmnurl.BuildEducationArticleNew(),
|
||||
RerenderUrl: hmnurl.BuildEducationRerender(),
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue