mirror of
https://git.sr.ht/~cadence/cloudtube
synced 2024-11-12 19:37:29 +00:00
Add home page and search page
This commit is contained in:
parent
cbc3a2bf67
commit
2cc6a2912a
14
api/search.js
Normal file
14
api/search.js
Normal file
@ -0,0 +1,14 @@
|
||||
const fetch = require("node-fetch")
|
||||
const {render} = require("pinski/plugins")
|
||||
|
||||
module.exports = [
|
||||
{
|
||||
route: "/(?:search|results)", methods: ["GET"], code: async ({url}) => {
|
||||
const query = url.searchParams.get("q") || url.searchParams.get("search_query")
|
||||
const fetchURL = new URL("http://localhost:3000/api/v1/search")
|
||||
fetchURL.searchParams.set("q", query)
|
||||
const results = await fetch(fetchURL.toString()).then(res => res.json())
|
||||
return render(200, "pug/search.pug", {results})
|
||||
}
|
||||
}
|
||||
]
|
11
pug/home.pug
Normal file
11
pug/home.pug
Normal file
@ -0,0 +1,11 @@
|
||||
extends includes/layout.pug
|
||||
|
||||
block content
|
||||
main.home-page
|
||||
h1.top-header CloudTube
|
||||
h2.tagline An alternative front-end for YouTube.
|
||||
.encouraging-message
|
||||
p You're in control. Watch things your way.
|
||||
p Go on. What do you want to watch?
|
||||
form(method="get" action="/search").encouraging-search-form
|
||||
input(type="text" name="q" placeholder="I'd like to watch..." autocomplete="off").search.base-border-look
|
@ -10,6 +10,7 @@ html
|
||||
body.show-focus
|
||||
nav.main-nav
|
||||
a(href="/").link.home CloudTube
|
||||
input(type="text" placeholder="Search" name="q" autocomplete="off").search
|
||||
form(method="get" action="/search").search-form
|
||||
input(type="text" placeholder="Search" name="q" autocomplete="off").search
|
||||
|
||||
block content
|
||||
|
16
pug/includes/video-list-item.pug
Normal file
16
pug/includes/video-list-item.pug
Normal file
@ -0,0 +1,16 @@
|
||||
mixin video_list_item(video)
|
||||
- let link = `/watch?v=${video.videoId}`
|
||||
a(href=link).thumbnail
|
||||
img(src=`https://i.ytimg.com/vi/${video.videoId}/mqdefault.jpg` width=320 height=180 alt="").image
|
||||
span.duration= video.second__lengthText
|
||||
.info
|
||||
div.title: a(href=link).title-link= video.title
|
||||
div.author-line
|
||||
a(href=`/channel/${video.authorId}`).author= video.author
|
||||
if video.publishedText
|
||||
= ` • `
|
||||
span.published= video.publishedText
|
||||
= ` • `
|
||||
span.views= video.viewCountText || video.second__viewCountText
|
||||
if video.descriptionHtml
|
||||
div.description!= video.descriptionHtml
|
9
pug/search.pug
Normal file
9
pug/search.pug
Normal file
@ -0,0 +1,9 @@
|
||||
extends includes/layout.pug
|
||||
|
||||
include includes/video-list-item.pug
|
||||
|
||||
block content
|
||||
main.search-page
|
||||
each result in results
|
||||
.search-result
|
||||
+video_list_item(result)
|
@ -1,5 +1,7 @@
|
||||
extends includes/layout.pug
|
||||
|
||||
include includes/video-list-item.pug
|
||||
|
||||
block head
|
||||
title= video.title
|
||||
script(type="module" src=getStaticURL("html", "/static/js/player.js"))
|
||||
@ -56,13 +58,4 @@ block content
|
||||
h2.related-header Related videos
|
||||
each r in video.recommendedVideos
|
||||
.related-video
|
||||
- let link = `/watch?v=${r.videoId}`
|
||||
a(href=link).thumbnail
|
||||
img(src=`https://i.ytimg.com/vi/${r.videoId}/mqdefault.jpg` width=320 height=180 alt="").image
|
||||
span.duration= r.second__lengthText
|
||||
.info
|
||||
div.title: a(href=link).title-link= r.title
|
||||
div.author-line
|
||||
a(href=`/channel/${authorId}`).author= r.author
|
||||
= ` • `
|
||||
span.views= r.viewCountText
|
||||
+video_list_item(r)
|
||||
|
@ -18,6 +18,9 @@ input, select, button
|
||||
button
|
||||
cursor: pointer
|
||||
|
||||
:focus
|
||||
outline: none
|
||||
|
||||
:-moz-focusring
|
||||
outline: none
|
||||
|
||||
|
36
sass/includes/home-page.sass
Normal file
36
sass/includes/home-page.sass
Normal file
@ -0,0 +1,36 @@
|
||||
@use "colors.sass" as c
|
||||
|
||||
.home-page
|
||||
padding: 40px
|
||||
|
||||
.top-header
|
||||
font-size: 48px
|
||||
text-align: center
|
||||
|
||||
.tagline
|
||||
font-size: 30px
|
||||
text-align: center
|
||||
|
||||
.encouraging-message
|
||||
max-width: max-content
|
||||
margin: 0 auto
|
||||
text-align: center
|
||||
padding: 16px
|
||||
border-radius: 4px
|
||||
font-size: 20px
|
||||
background-color: c.$bg-darker
|
||||
color: c.$fg-main
|
||||
|
||||
p
|
||||
margin: 0 32px
|
||||
|
||||
&:not(:last-child)
|
||||
margin-bottom: 0.6em
|
||||
|
||||
.encouraging-search-form
|
||||
display: flex
|
||||
|
||||
.search
|
||||
margin-top: 16px
|
||||
flex: 1
|
||||
font-size: 18px
|
44
sass/includes/search-page.sass
Normal file
44
sass/includes/search-page.sass
Normal file
@ -0,0 +1,44 @@
|
||||
@use "video-list-item.sass" as *
|
||||
@use "colors.sass" as c
|
||||
|
||||
.search-page
|
||||
padding: 40px 20px 20px
|
||||
max-width: 900px
|
||||
margin: 0 auto
|
||||
|
||||
.search-result
|
||||
@include video-list-item
|
||||
|
||||
grid-gap: 16px
|
||||
grid-template-columns: 240px 1fr
|
||||
margin-bottom: 20px
|
||||
overflow: hidden
|
||||
|
||||
.image
|
||||
width: 240px
|
||||
height: 135px
|
||||
|
||||
.duration
|
||||
font-size: 17px
|
||||
padding: 4px 5px
|
||||
right: 5px
|
||||
bottom: 5px
|
||||
|
||||
.title
|
||||
font-size: 24px
|
||||
|
||||
.author-line
|
||||
font-size: 15px
|
||||
color: c.$fg-main
|
||||
|
||||
.author
|
||||
color: c.$fg-main
|
||||
|
||||
.description
|
||||
margin-top: 16px
|
||||
font-size: 15px
|
||||
color: c.$fg-dim
|
||||
|
||||
b
|
||||
font-weight: normal
|
||||
color: c.$fg-main
|
50
sass/includes/video-list-item.sass
Normal file
50
sass/includes/video-list-item.sass
Normal file
@ -0,0 +1,50 @@
|
||||
@use "colors.sass" as c
|
||||
|
||||
@mixin video-list-item
|
||||
display: grid
|
||||
grid-template-columns: 160px 1fr
|
||||
grid-gap: 8px
|
||||
align-items: start
|
||||
align-content: start
|
||||
margin-bottom: 12px
|
||||
|
||||
.thumbnail
|
||||
position: relative
|
||||
display: flex
|
||||
background: c.$bg-darkest
|
||||
|
||||
.image
|
||||
width: 160px
|
||||
height: 90px
|
||||
|
||||
.duration
|
||||
position: absolute
|
||||
bottom: 3px
|
||||
right: 3px
|
||||
color: c.$fg-bright
|
||||
font-size: 14px
|
||||
background: rgba(20, 20, 20, 0.85)
|
||||
line-height: 1
|
||||
padding: 3px 5px 4px
|
||||
border-radius: 4px
|
||||
|
||||
.title
|
||||
font-size: 15px
|
||||
line-height: 1.2
|
||||
|
||||
.title-link
|
||||
color: c.$fg-main
|
||||
text-decoration: none
|
||||
|
||||
.author-line
|
||||
margin-top: 4px
|
||||
font-size: 15px
|
||||
color: c.$fg-dim
|
||||
|
||||
.author
|
||||
color: c.$fg-dim
|
||||
text-decoration: none
|
||||
|
||||
&:hover, &:active
|
||||
color: c.$fg-bright
|
||||
text-decoration: underline
|
@ -1,4 +1,5 @@
|
||||
@use "colors.sass" as c
|
||||
@use "video-list-item.sass" as *
|
||||
|
||||
.video-page
|
||||
display: grid
|
||||
@ -44,7 +45,8 @@
|
||||
.info-secondary
|
||||
display: flex
|
||||
flex-direction: column
|
||||
align-items: end
|
||||
align-items: flex-end
|
||||
text-align: right
|
||||
margin-top: 6px
|
||||
margin-left: 6px
|
||||
|
||||
@ -68,50 +70,4 @@
|
||||
font-size: 26px
|
||||
|
||||
.related-video
|
||||
display: grid
|
||||
grid-template-columns: 160px 1fr
|
||||
grid-gap: 8px
|
||||
align-items: start
|
||||
align-content: start
|
||||
margin-bottom: 16px
|
||||
|
||||
.thumbnail
|
||||
position: relative
|
||||
display: flex
|
||||
background: c.$bg-darkest
|
||||
|
||||
.image
|
||||
width: 160px
|
||||
height: 90px
|
||||
|
||||
.duration
|
||||
position: absolute
|
||||
bottom: 3px
|
||||
right: 3px
|
||||
color: c.$fg-bright
|
||||
font-size: 14px
|
||||
background: rgba(20, 20, 20, 0.85)
|
||||
line-height: 1
|
||||
padding: 3px 5px 4px
|
||||
border-radius: 4px
|
||||
|
||||
.title
|
||||
font-size: 15px
|
||||
line-height: 1.2
|
||||
|
||||
.title-link
|
||||
color: c.$fg-main
|
||||
text-decoration: none
|
||||
|
||||
.author-line
|
||||
margin-top: 4px
|
||||
font-size: 15px
|
||||
color: c.$fg-dim
|
||||
|
||||
.author
|
||||
color: c.$fg-dim
|
||||
text-decoration: none
|
||||
|
||||
&:hover, &:active
|
||||
color: c.$fg-bright
|
||||
text-decoration: underline
|
||||
@include video-list-item
|
||||
|
@ -2,6 +2,8 @@
|
||||
@use "includes/colors.sass" as c
|
||||
@use "sass:selector"
|
||||
@use "includes/video-page.sass"
|
||||
@use "includes/search-page.sass"
|
||||
@use "includes/home-page.sass"
|
||||
|
||||
@font-face
|
||||
font-family: "Bariol"
|
||||
@ -52,6 +54,9 @@
|
||||
&:active
|
||||
background-color: c.$bg-dark
|
||||
|
||||
.base-border-look
|
||||
@include border-button
|
||||
|
||||
.border-look
|
||||
@include border-button
|
||||
@include button-size
|
||||
@ -78,11 +83,17 @@
|
||||
&:focus, &:hover
|
||||
background-color: c.$bg-accent-x
|
||||
|
||||
.search
|
||||
@include button-bg
|
||||
.search-form
|
||||
display: flex
|
||||
flex: 1
|
||||
margin: 1px
|
||||
align-items: center
|
||||
|
||||
&:hover, &:focus
|
||||
border: 1px solid c.$edge-grey
|
||||
margin: 0px
|
||||
.search
|
||||
@include button-bg
|
||||
padding: 10px
|
||||
flex: 1
|
||||
margin: 1px
|
||||
|
||||
&:hover, &:focus
|
||||
border: 1px solid c.$edge-grey
|
||||
margin: 0px
|
||||
|
@ -13,6 +13,7 @@ server.addSassDir("sass", ["sass/includes"])
|
||||
server.addRoute("/static/css/main.css", "sass/main.sass", "sass")
|
||||
|
||||
server.addPugDir("pug", ["pug/includes"])
|
||||
server.addRoute("/", "pug/home.pug", "pug")
|
||||
|
||||
server.addStaticHashTableDir("html/static/js")
|
||||
server.addStaticHashTableDir("html/static/js/elemjs")
|
||||
@ -20,7 +21,3 @@ server.addStaticHashTableDir("html/static/js/elemjs")
|
||||
server.addAPIDir("api")
|
||||
|
||||
server.startServer()
|
||||
|
||||
setTimeout(() => {
|
||||
console.log(server.staticFileTable, server.pageHandlers)
|
||||
}, 2000)
|
||||
|
Loading…
Reference in New Issue
Block a user