Add 6 new themes, stars to homepage
Some checks reported errors
continuous-integration/drone/push Build was killed
continuous-integration/drone/promote/production Build is passing

This commit is contained in:
Garrett Mills 2023-08-17 01:10:46 -05:00
parent 58c31c90c1
commit b6b07f2cad
8 changed files with 345 additions and 3 deletions

View File

@ -137,5 +137,101 @@ export default {
line3: '#efe2df', line3: '#efe2df',
highlightTheme: 'base16/atelier-cave-light', highlightTheme: 'base16/atelier-cave-light',
}, },
americana: {
displayName: "Americana",
background: '#f6f4f3',
backgroundOffset: 'rgba(120, 153, 185, 0.1)',
backgroundOffset2: 'rgba(120, 153, 185, 0.2)',
hero: '#17396e',
font: '#af5b5b',
fontMuted: '#276fbf',
box: '#7899b9',
link: 'var(--c-hero)',
noiseSize: '100px',
line3: '#af5b5b',
line1: '#17396e',
line2: '#276fbf',
highlightTheme: 'base16/atelier-cave-light',
},
ubuntu: {
displayName: "Ubuntu",
background: '#333333',
backgroundOffset: 'rgba(51, 51, 51, 0.4)',
backgroundOffset2: 'rgba(51, 51, 51, 0.6)',
hero: '#e95420',
font: '#ccc',
fontMuted: '#aea79f',
box: '#604358',
link: 'var(--c-hero)',
noiseSize: '100px',
line1: '#56334B',
line2: '#7E5273',
line3: '#ED764D',
highlightTheme: 'base16/atelier-cave-light',
},
mintMono: {
displayName: "Mint Mono",
background: '#6b9080',
backgroundOffset: 'rgba(164, 195, 178, 0.2)',
backgroundOffset2: 'rgba(51, 51, 51, 0.6)',
hero: '#eaf4f4',
font: '#cce3de',
fontMuted: '#a4c3b2',
box: '#a4c3b2',
link: 'var(--c-hero)',
noiseSize: '100px',
line1: '#a4c3b2',
line2: '#cce3de',
line3: '#f6fff8',
highlightTheme: 'base16/atelier-cave-light',
},
abyss: {
displayName: "Abyss",
background: '#010A19',
backgroundOffset: 'rgba(1, 10, 25, 0.2)',
backgroundOffset2: 'rgba(1, 10, 25, 0.6)',
hero: '#6c7a96',
font: '#afbed3',
fontMuted: '#8391a7',
box: '#061021',
link: '#8391a7',
noiseSize: '100px',
line1: '#19253b',
line2: '#0b1629',
line3: '#061021',
highlightTheme: 'base16/atelier-cave-light',
},
blackIsBack: {
displayName: 'Black Is The New Black',
background: '#e4e4e4',
backgroundOffset: 'rgba(188, 188, 188, 0.2)',
backgroundOffset2: 'rgba(188, 188, 188, 0.6)',
hero: '#111',
font: '#4c4c4c',
fontMuted: '#4c4c4c',
box: '#111',
link: '#111',
noiseSize: '100px',
line1: '#333',
line2: '#222',
line3: '#111',
highlightTheme: 'base16/atelier-cave-light',
},
noir: {
displayName: "Noir",
background: '#2a333f',
backgroundOffset: 'rgba(56, 53, 60, 0.3)',
backgroundOffset2: 'rgb(45, 80, 96, 0.2)',
hero: '#5c3d51',
font: '#7297a8',
fontMuted: '#557988',
box: '#c3984f',
link: 'var(--c-box)',
noiseSize: '100px',
line1: '#c3984f',
line2: '#2d5060',
line3: '#5c3d51',
highlightTheme: 'base16/atelier-estuary',
},
} as Record<string, ColorPalette>, } as Record<string, ColorPalette>,
} }

View File

@ -161,7 +161,7 @@ export class Home extends Controller {
const themeKeys = Object.keys(themes) const themeKeys = Object.keys(themes)
const themeName = this.session.get('theme.name') const themeName = this.session.get('theme.name')
// const themeName = this.request.safe('theme').or(themeKeys[Math.floor(Math.random()*themeKeys.length)]).in(themeKeys) // const themeName = this.request.safe('theme').or(themeKeys[Math.floor(Math.random()*themeKeys.length)]).in(themeKeys)
const theme = themes[themeName] const theme = themes[themeName] || themes[themeKeys[0]]
const themeCSS = ` const themeCSS = `
:root { :root {
--c-background: ${theme.background}; --c-background: ${theme.background};

View File

@ -135,6 +135,7 @@ b {
.section-border .section-border-inner-1 { .section-border .section-border-inner-1 {
border-top: 15px solid var(--c-line-1); border-top: 15px solid var(--c-line-1);
border-bottom: 15px solid var(--c-line-3); border-bottom: 15px solid var(--c-line-3);
background: var(--c-line-2);
transform: rotate(3deg); transform: rotate(3deg);
width: calc(100vw + 30px); width: calc(100vw + 30px);
margin-left: -15px; margin-left: -15px;
@ -433,6 +434,24 @@ footer .auth-container .profile {
margin-right: 15px; margin-right: 15px;
margin-top: 15px; margin-top: 15px;
} }
footer.theme-stats {
padding-bottom: 3px;
background: var(--c-background-offset-2);
}
footer.theme-stats ul {
padding: 0;
}
footer.theme-stats li {
display: inline;
font-family: "Courier New", Courier, monospace;
font-size: 0.8em;
text-transform: uppercase;
color: var(--c-font-muted);
}
.button-links { .button-links {
margin: 20px; margin: 20px;
} }
@ -466,6 +485,9 @@ footer .auth-container .profile {
footer .links { footer .links {
padding: 20px 0 0; padding: 20px 0 0;
} }
footer.theme-stats li {
display: block;
}
h2 { h2 {
font-size: 36pt; font-size: 36pt;
line-height: 1.6em; line-height: 1.6em;
@ -488,6 +510,27 @@ footer .auth-container .profile {
background-color: var(--c-background-offset); background-color: var(--c-background-offset);
margin-bottom: 120px; margin-bottom: 120px;
} }
.hero .stars svg {
color: var(--c-hero) !important;
position: absolute;
top: 0;
left: 0;
opacity: 0.2;
}
#star-1, #star-3, #star-5 {
height: 50px;
}
#star-2, #star-6 {
height: 75px;
}
#star-4 {
height: 100px;
}
.hero h1 { .hero h1 {
font-weight: 300; font-weight: 300;
font-size: 9em; font-size: 9em;

View File

@ -0,0 +1,52 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
width="47.581146mm"
height="78.547104mm"
viewBox="0 0 47.581146 78.547104"
version="1.1"
id="svg5"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns="http://www.w3.org/2000/svg"
xmlns:svg="http://www.w3.org/2000/svg">
<sodipodi:namedview
id="namedview7"
pagecolor="#ffffff"
bordercolor="currentColor"
borderopacity="0.25"
inkscape:showpageshadow="2"
inkscape:pageopacity="0.0"
inkscape:pagecheckerboard="0"
inkscape:deskcolor="#d1d1d1"
inkscape:document-units="mm"
showgrid="false" />
<defs
id="defs2" />
<g
inkscape:label="Layer 1"
inkscape:groupmode="layer"
id="layer1"
transform="translate(-81.41733,-109.42827)">
<path
style="fill:currentColor;fill-opacity:0;stroke:currentColor;stroke-width:7;stroke-linecap:round;stroke-dasharray:none"
d="m 105,112.92827 c 0,0 1.66434,35.57173 -20.082663,35.57173"
id="path1153"
inkscape:export-filename="star.svg"
inkscape:export-xdpi="96"
inkscape:export-ydpi="96" />
<path
style="fill:currentColor;fill-opacity:0;stroke:currentColor;stroke-width:7;stroke-linecap:round;stroke-dasharray:none"
d="m 105.41582,112.92827 c 0,0 -1.66434,35.57173 20.08267,35.57173"
id="path1153-3" />
<path
style="fill:currentColor;fill-opacity:0;stroke:currentColor;stroke-width:7;stroke-linecap:round;stroke-dasharray:none"
d="m 105,184.47538 c 0,0 1.66434,-35.57173 -20.082665,-35.57173"
id="path1153-6" />
<path
style="fill:currentColor;fill-opacity:0;stroke:currentColor;stroke-width:7;stroke-linecap:round;stroke-dasharray:none"
d="m 105.41582,184.47538 c 0,0 -1.66434,-35.57173 20.08267,-35.57173"
id="path1153-3-7" />
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

@ -1,5 +1,7 @@
window.glmdev = window.glmdev || {} window.glmdev = window.glmdev || {}
window.glmdev.themeStats = window.glmdev.themeStats || []
window.glmdev.taglines = [ window.glmdev.taglines = [
'...is proud that this site is Google-free', '...is proud that this site is Google-free',
'...is a supporter of FLOSS', '...is a supporter of FLOSS',
@ -20,7 +22,7 @@ window.glmdev.taglines = [
] ]
document.querySelector('#tagline') document.querySelector('#tagline')
.addEventListener('click', event => { ?.addEventListener('click', event => {
if ( typeof glmdev.tagline_index === 'undefined' ) glmdev.tagline_index = 0 if ( typeof glmdev.tagline_index === 'undefined' ) glmdev.tagline_index = 0
else if ( glmdev.tagline_index === glmdev.taglines.length - 1 ) glmdev.tagline_index = 0 else if ( glmdev.tagline_index === glmdev.taglines.length - 1 ) glmdev.tagline_index = 0
else glmdev.tagline_index += 1 else glmdev.tagline_index += 1
@ -29,7 +31,7 @@ document.querySelector('#tagline')
}) })
document.querySelector('#timeline-view-all') document.querySelector('#timeline-view-all')
.addEventListener('click', event => { ?.addEventListener('click', event => {
const hidden = document.querySelectorAll('.work-container.theme-hide') const hidden = document.querySelectorAll('.work-container.theme-hide')
for ( const item of hidden ) { for ( const item of hidden ) {
item.classList.remove('theme-hide') item.classList.remove('theme-hide')
@ -37,3 +39,125 @@ document.querySelector('#timeline-view-all')
document.querySelector('#timeline-view-all').classList.add('theme-hide') document.querySelector('#timeline-view-all').classList.add('theme-hide')
}, false) }, false)
function getRandomArbitrary(min, max) {
min = Math.ceil(min)
max = Math.floor(max)
return Math.floor(Math.random() * (max - min + 1)) + min
}
const calculateMean = (values) => {
return (values.reduce((sum, current) => sum + current)) / values.length;
}
const calculateVariance = (values) => {
const average = calculateMean(values);
const squareDiffs = values.map((value) => {
const diff = value - average;
return diff * diff;
});
return calculateMean(squareDiffs);
}
const calculateStdev = (values) => {
return Math.sqrt(calculateVariance(values))
}
function calculateDistance(ax, ay, bx, by) {
return Math.sqrt(Math.pow(ax-bx, 2) + Math.pow(ay-by, 2))
}
function placeStars() {
const widths = []
const heights = []
document.querySelectorAll('.stars svg')
.forEach(function(star) {
var width = window.innerWidth - 50
var height = (window.innerHeight / 3) - 50
var widthOffset = getRandomArbitrary(50, width)
var heightOffset = getRandomArbitrary(50, height)
star.style.left = widthOffset + 'px'
star.style.top = heightOffset + 'px'
widths.push(widthOffset)
heights.push(heightOffset)
})
return [widths, heights]
}
function isGoodStarPattern(widths, heights) {
const starCount = document.querySelectorAll('.stars svg').length
const minWidthStdev = window.innerWidth / (starCount / 1.5)
const widthStdev = calculateStdev(widths)
const minHeightStdev = (window.innerHeight / 3) / (starCount)
const heightStdev = calculateStdev(heights)
const [centroidWidth, centroidHeight] = [window.innerWidth / 2, (window.innerHeight / 3) / 2]
const distances = widths.map((w, i) => [w, heights[i]])
.map(([w, h]) => calculateDistance(w, h, centroidWidth, centroidHeight))
const minDistanceStdev = Math.min(window.innerWidth, window.innerHeight) / 10
const distanceStdev = calculateStdev(distances)
return widthStdev > minWidthStdev && heightStdev > minHeightStdev && distanceStdev > minDistanceStdev
}
function placeStarsWithRetry() {
if ( !document.querySelectorAll('.stars svg').length ) {
return
}
let tries = 30
do {
var [widths, heights] = placeStars()
tries -= 1
} while ( !isGoodStarPattern(widths, heights) && tries > 0 )
const [centroidWidth, centroidHeight] = [window.innerWidth / 2, (window.innerHeight / 3) / 2]
const distances = widths.map((w, i) => [w, heights[i]])
.map(([w, h]) => calculateDistance(w, h, centroidWidth, centroidHeight))
window.glmdev.themeStats.push(
`# of constellations generated: ${30 - tries}`,
`Width stdev: ${Math.round(calculateStdev(widths))}`,
`Height stdev: ${Math.round(calculateStdev(heights))}`,
`Distance stdev: ${Math.round(calculateStdev(distances))}`
)
}
window.placeStars = placeStars
window.isGoodStarPattern = isGoodStarPattern
window.placeStarsWithRetry = placeStarsWithRetry
placeStarsWithRetry()
function updateThemeStatsDisplay() {
const ul = document.querySelector('footer.theme-stats ul')
for ( const stat of glmdev.themeStats ) {
const li = document.createElement('li')
li.innerText = stat
ul.appendChild(li)
}
ul.style.display = glmdev.themeStats.length ? 'unset' : 'none'
}
var resizeDebufHandle = false
window.onresize = () => {
if ( resizeDebufHandle ) {
clearTimeout(resizeDebufHandle)
}
resizeDebufHandle = setTimeout(() => {
placeStarsWithRetry()
resizeDebufHandle = false
}, 500)
}
window.updateThemeStatsDisplay = updateThemeStatsDisplay
updateThemeStatsDisplay()

View File

@ -24,6 +24,15 @@ block content
br br
br br
h4 The Stars
p The homepage of this site features a constellation of 6 translucent stars which appears at the top of the page.
p The positions of the stars are randomly generated based on the dimensions of the page. To discourage clustered/skewed constellations, the following criteria are used:
ol
li Standard deviation of the x-axis offset
li Standard deviation of the y-axis offset
li Standard deviation of the centroid distance
p Because it's interesting, you can view the # of generation attempts, as well as the aforementioned criteria in the footer of the homepage.
h3 Source Code & Licensing h3 Source Code & Licensing
a(href='https://creativecommons.org/licenses/by-nc-sa/4.0/' target='_blank' style='margin-top: 15px') a(href='https://creativecommons.org/licenses/by-nc-sa/4.0/' target='_blank' style='margin-top: 15px')
img(src=asset('cc-by-nc-sa.png')) img(src=asset('cc-by-nc-sa.png'))

View File

@ -17,6 +17,10 @@ head
block style block style
style !{themeCSS} style !{themeCSS}
script.
window.glmdev = window.glmdev || {}
window.glmdev.themeStats = window.glmdev.themeStats || []
window.glmdev.themeStats.push('Theme: !{themeDisplayName}')
link(rel='stylesheet' href=asset('main-70s.css')) link(rel='stylesheet' href=asset('main-70s.css'))
link(rel='author' href='/humans.txt') link(rel='author' href='/humans.txt')
@ -81,5 +85,8 @@ body
li li
a(href='/dash') dashboard a(href='/dash') dashboard
footer.theme-stats
ul
block script block script
script(src=asset('welcome.js')) script(src=asset('welcome.js'))

View File

@ -3,6 +3,17 @@ block content
.container#home .container#home
.inner .inner
section.hero.full-height section.hero.full-height
.stars
each val in [1, 2, 3, 4, 5, 6]
svg(id=('star-' + val) width='47.581146mm' height='78.547104mm' viewbox='0 0 47.581146 78.547104' version='1.1' xmlns:inkscape='http://www.inkscape.org/namespaces/inkscape' xmlns:sodipodi='http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd' xmlns='http://www.w3.org/2000/svg' xmlns:svg='http://www.w3.org/2000/svg')
sodipodi:namedview#namedview7(pagecolor='#ffffff' bordercolor='currentColor' borderopacity='0.25' inkscape:showpageshadow='2' inkscape:pageopacity='0.0' inkscape:pagecheckerboard='0' inkscape:deskcolor='#d1d1d1' inkscape:document-units='mm' showgrid='false')
defs#defs2
g#layer1(inkscape:label='Layer 1' inkscape:groupmode='layer' transform='translate(-81.41733,-109.42827)')
path#path1153(style='fill:currentColor;fill-opacity:0;stroke:currentColor;stroke-width:7;stroke-linecap:round;stroke-dasharray:none' d='m 105,112.92827 c 0,0 1.66434,35.57173 -20.082663,35.57173' inkscape:export-filename='star.svg' inkscape:export-xdpi='96' inkscape:export-ydpi='96')
path#path1153-3(style='fill:currentColor;fill-opacity:0;stroke:currentColor;stroke-width:7;stroke-linecap:round;stroke-dasharray:none' d='m 105.41582,112.92827 c 0,0 -1.66434,35.57173 20.08267,35.57173')
path#path1153-6(style='fill:currentColor;fill-opacity:0;stroke:currentColor;stroke-width:7;stroke-linecap:round;stroke-dasharray:none' d='m 105,184.47538 c 0,0 1.66434,-35.57173 -20.082665,-35.57173')
path#path1153-3-7(style='fill:currentColor;fill-opacity:0;stroke:currentColor;stroke-width:7;stroke-linecap:round;stroke-dasharray:none' d='m 105.41582,184.47538 c 0,0 -1.66434,-35.57173 20.08267,-35.57173')
.hero-box .hero-box
h1 Garrett Mills h1 Garrett Mills
p Software engineer, computer scientist, and nerd. p Software engineer, computer scientist, and nerd.