treehouse/static/css/main.css

917 lines
17 KiB
CSS

/* Color scheme. */
:root {
/* naturally */
--liquidex-brand-blue: #058ef0;
/* but also: */
--liquidex-brand-red: #eb134a;
--liquidex-brand-yellow: #ffc31f;
--liquidex-brand-green: #06ca4a;
--text-color-light: #55423e;
--link-color-light: #004ec8;
--link-color-visited-light: #6c2380;
--background-color: rgb(255, 253, 246);
--background-color-tooltip: rgb(226, 223, 214);
--text-color: #55423e;
--link-color: #004ec8;
--link-color-visited: #6c2380;
--shaded-background: rgba(0, 0, 0, 5%);
--border-1: rgba(0, 0, 0, 15%);
--border-2: rgba(0, 0, 0, 30%);
--hover: rgba(0, 0, 0, 15%);
}
@media (prefers-color-scheme: dark) {
:root {
--background-color: rgb(30, 40, 53);
--background-color-tooltip: rgb(23, 31, 41);
--text-color: #d7cdbf;
--link-color: #93cce8;
--link-color-visited: #f7afde;
--shaded-background: #f7e5df0c;
--border-0: #f7e5df1a;
--border-1: #f7e5df26;
--border-1-and-a-half: #f7e5df3a;
--border-2: #f7e5df4d;
}
}
:root {
/* Font size-responsive measurements. treehouse was designed against a font size of 14px;
each of these sizes is (n / 14)rem where n is the number of pixels. */
--1px: 0.07142857143rem;
--2px: 0.1428571429rem;
--3px: 0.2142857143rem;
--4px: 0.2857142857rem;
--6px: 0.4285714286rem;
--8px: 0.5714285714rem;
--10px: 0.7142857143rem;
--12px: 0.8571428571rem;
--16px: 1.142857143rem;
}
/* Article-style layout. Center everything and give it a maximum width */
body {
max-width: 1200px;
margin-left: auto;
margin-right: auto;
display: flex;
flex-direction: column;
}
main {
padding: 0 var(--16px);
}
@media screen and (max-width: 480px) {
main {
padding: 0 var(--8px);
}
}
/* Choose more pretty colors than vanilla HTML */
:root {
scrollbar-color: var(--border-2) var(--shaded-background);
scrollbar-width: auto;
scrollbar-gutter: stable;
}
body {
background-color: var(--background-color);
color: var(--text-color);
}
body::selection {
/* Even though this color doesn't yield the most readable text, browsers */
background-color: var(--liquidex-brand-blue);
}
/* Set up typography */
@font-face {
font-family: 'RecVar';
/* NOTE: I put the hash in here manually instead of adding the complexity of piping CSS through
Handlebars because I don't really think it's worth it for this single asset.
Other assets are referenced rarely enough that caching probably isn't gonna make too much of
an impact.
It's unlikely I'll ever update the font anyways, so eh, whatever. */
src: url('../font/Recursive_VF_1.085.woff2?cache=b3-445487d5');
}
@font-face {
font-family: 'RecVarMono';
src: url('../font/Recursive_VF_1.085.woff2?cache=b3-445487d5');
font-variation-settings: "MONO" 1.0;
}
body,
pre,
code,
kbd,
button {
font-family: 'RecVar', sans-serif;
line-height: 1.5;
}
body {
font-size: 87.5%;
}
pre,
code,
kbd,
button {
font-size: 100%;
}
:root {
--recursive-mono: 0.0;
--recursive-casl: 1.0;
--recursive-wght: 400;
--recursive-slnt: 0.0;
--recursive-crsv: 0.5;
--recursive-simplified-f: "ss03";
--recursive-simplified-g: "ss04";
--recursive-simplified-l: "ss05";
--recursive-simplified-r: "ss06";
--recursive-no-serif-L-Z: "ss08";
}
*,
*:before,
*:after {
font-variation-settings:
"MONO" var(--recursive-mono),
"CASL" var(--recursive-casl),
"wght" var(--recursive-wght),
"slnt" var(--recursive-slnt),
"CRSV" var(--recursive-crsv);
font-feature-settings:
var(--recursive-simplified-f),
var(--recursive-simplified-g),
var(--recursive-simplified-l),
var(--recursive-simplified-r),
var(--recursive-no-serif-L-Z);
}
h1 {
--recursive-slnt: 0.0;
--recursive-casl: 0.0;
--recursive-wght: 900;
font-size: 3.5rem;
font-feature-settings: var(--recursive-simplified-r) 0;
}
h2 {
--recursive-slnt: 0.0;
--recursive-casl: 0.5;
--recursive-wght: 800;
font-size: 2rem;
}
h3 {
--recursive-slnt: 0.0;
--recursive-casl: 0.5;
--recursive-wght: 700;
font-size: 1.5rem;
}
h4 {
--recursive-slnt: 0.0;
--recursive-casl: 0.5;
--recursive-wght: 700;
font-size: 1rem;
}
pre,
code,
kbd,
th-literate-program {
--recursive-mono: 1.0;
--recursive-casl: 0.0;
--recursive-slnt: 0.0;
--recursive-wght: 450;
}
b,
strong {
--recursive-wght: 700;
}
i,
em {
--recursive-slnt: -16.0;
font-style: normal;
}
/* Lay out elements a bit more compactly */
p,
pre {
margin: 0 0;
}
h1,
h2,
h3,
h4,
h5,
h6 {
margin: var(--4px) 0;
}
/* Lay out elements a little less compactly (actually just have some blank space past the end) */
body {
padding-bottom: 10rem;
}
/* Make code examples a little prettier by giving them visual separation from the rest of the page */
code,
th-literate-program {
padding: var(--3px) var(--4px);
background-color: var(--shaded-background);
border-radius: 0.4em;
}
th-literate-program,
th-literate-output {
display: block;
}
kbd {
padding: var(--3px) var(--6px);
border: var(--1px) solid var(--border-1);
border-radius: 0.4em;
}
pre,
th-literate-program {
padding: var(--8px) var(--12px);
margin: var(--12px) 0;
background-color: var(--shaded-background);
border-radius: 0.5em;
transition: background-color var(--transition-duration);
}
@media (prefers-color-scheme: light) {
pre,
th-literate-program {
background-color: transparent;
border: var(--1px) solid var(--border-1);
}
}
pre>code,
th-literate-program>code {
padding: 0;
background: none;
border-radius: 0;
}
th-literate-program {
white-space: pre;
}
/* And don't let code examples fly off and overflow the window */
pre,
th-literate-program {
min-width: 0;
width: auto;
overflow: auto;
}
/* Also don't let images get out of hand */
img {
max-width: 100%;
}
/* Also regarding images - make them look a bit more pretty by default */
img.pic {
border-radius: var(--6px);
margin: var(--8px) 0;
}
/* Image hints for tweaking rendering */
img {
&[src*='+pixel'] {
image-rendering: pixelated;
border-radius: 0;
}
/* TODO: These could be autogenerated! */
&[src*='+width72'] {
width: 72px;
height: auto;
}
&[src*='+width160'] {
width: 160px;
height: auto;
}
&[src*='+width640'] {
width: 640px;
height: auto;
}
&[src*='+width752'] {
width: 752px;
height: auto;
}
/* Resources for use in JavaScript. */
&.resource {
display: none;
}
}
/* Fix the default blue and ugly purple links normally have */
a {
color: var(--link-color);
}
a:visited {
color: var(--link-color-visited);
}
/* Allow for some secret links */
a.secret {
color: var(--text-color);
text-decoration: none;
}
/* Make blockquotes a bit prettier */
blockquote {
margin: 0;
padding: var(--4px) var(--12px);
margin: var(--4px) 0;
border-left: var(--4px) solid var(--border-1);
}
/* And tables. */
table {
margin: var(--8px) 0;
}
table,
th,
td {
border: var(--1px) solid var(--border-2);
border-collapse: collapse;
padding: var(--4px) var(--10px);
}
th {
background-color: var(--shaded-background);
--recursive-wght: 700;
--recursive-casl: 0.5;
}
/* Horizontal rules */
hr {
width: 100%;
border: none;
border-top: var(--1px) solid var(--border-1);
margin-top: 2em;
margin-bottom: 2em;
}
/* Style the noscript box a little more prettily. */
.noscript {
padding: var(--16px);
background-color: #fde748;
color: var(--text-color-light);
border: var(--1px) solid #6c581c;
border-radius: var(--8px);
width: fit-content;
margin-left: auto;
margin-right: auto;
}
.noscript p {
margin-top: 0;
margin-bottom: var(--16px);
}
.noscript p:last-child {
margin-bottom: 0;
}
.noscript a {
color: var(--link-color-light);
}
.noscript a:visited {
color: var(--link-color-visited-light);
}
/* also, webkit. */
#webkit-makes-me-go-insane {
display: none;
}
/* Style the navigation bar. */
nav {
display: flex;
align-items: center;
}
nav .nav-page {
display: flex;
flex-grow: 1;
flex-direction: column;
}
/* Give the logo on the top some nicer looks */
nav .logo {
width: 48px;
height: 48px;
padding: 16px;
display: block;
opacity: 100%;
color: var(--text-color);
}
/* Style page titles */
h1.page-title {
--recursive-wght: 800;
margin-top: 0;
margin-bottom: 0;
margin-left: 2.25rem;
font-size: 1.25rem;
& a {
color: var(--text-color);
text-decoration: none;
&:hover {
text-decoration: underline;
}
}
}
@media (hover: none) {
h1.page-title a {
text-decoration: underline;
}
}
/* Style the `new` link on the homepage */
a[data-cast~="new"] {
flex-shrink: 0;
color: var(--text-color);
opacity: 50%;
margin-right: var(--16px);
&.has-news {
opacity: 100%;
text-decoration: none;
& .new-text {
text-decoration: underline;
}
}
& .badge {
margin-left: var(--8px);
text-decoration: none;
}
}
/* Style new badges */
span.badge {
--recursive-wght: 800;
--recursive-slnt: 0;
--recursive-mono: 1.0;
--recursive-casl: 0;
border-radius: 999px;
padding: var(--2px) var(--6px);
font-size: 0.9em;
&.red {
color: white;
background-color: #d01243;
}
&.blue {
color: white;
background-color: #058ef0;
}
&.before-content {
margin-right: var(--6px);
}
}
/* Style the footer */
footer {
margin-top: 4rem;
padding-right: 1.75rem;
text-align: right;
display: flex;
flex-direction: row;
& #version-info {
flex-grow: 1;
}
& #footer-icon {
flex-shrink: 0;
}
& #version-info {
display: flex;
flex-direction: row;
align-items: center;
justify-content: end;
opacity: 50%;
padding-left: 1.75rem;
transition: var(--transition-duration) opacity;
& .icon-history {
display: inline-block;
width: 24px;
height: 24px;
padding-right: 1.75rem;
background-image: var(--icon-history);
background-repeat: no-repeat;
background-position: 50% 50%;
}
&>ul {
display: flex;
flex-direction: row;
list-style: none;
margin: 0;
padding-left: 0;
opacity: 0%;
transition: var(--transition-duration) opacity;
}
&>ul>li:not(:first-child)::before {
content: '·';
text-decoration: none;
display: inline-block;
padding-left: 0.75em;
padding-right: 0.75em;
}
& a {
display: inline-block;
color: var(--text-color);
}
&:hover>ul {
opacity: 100%;
}
}
& #footer-icon {
display: flex;
padding-right: 1.75rem;
&>a {
display: flex;
flex-direction: row;
}
&>a>svg {
display: flex;
color: var(--text-color);
opacity: 40%;
}
}
}
/* Style emojis to be readable */
img[data-cast~="emoji"] {
max-width: 1.5em;
max-height: 1.5em;
vertical-align: bottom;
object-fit: contain;
}
/* And also style emoji tooltips. */
th-emoji-tooltip {
display: flex;
flex-direction: column;
align-items: center;
position: fixed;
transform: translateX(-50%) translateY(-10%) scale(0.8);
width: max-content;
z-index: 100;
background-color: var(--background-color-tooltip);
padding: var(--8px);
margin-top: var(--8px);
border-radius: var(--6px);
transition:
opacity var(--transition-duration) cubic-bezier(0.22, 1, 0.36, 1),
filter var(--transition-duration) cubic-bezier(0.22, 1, 0.36, 1),
transform var(--transition-duration) cubic-bezier(0.22, 1, 0.36, 1);
opacity: 0%;
filter: blur(var(--3px));
pointer-events: none;
}
th-emoji-tooltip.transitioned-in {
opacity: 100%;
filter: blur(0);
transform: translateX(-50%) scale(1.0);
}
th-emoji-tooltip img {
display: block;
max-width: 4.5rem;
max-height: 4.5rem;
}
th-emoji-tooltip p {
--recursive-wght: 550;
color: var(--text-color);
font-size: 0.9em;
margin: 0;
padding-top: 6px;
line-height: 1;
}
.th-emoji-unknown {
text-decoration: 1px underline var(--error-color);
cursor: help;
}
/* Funny joke */
@keyframes hello-there {
0% {
opacity: 0%;
}
70% {
opacity: 0%;
}
100% {
opacity: 70%;
}
}
.oops-you-seem-to-have-gotten-stuck {
margin-top: 16px;
display: none;
position: absolute;
opacity: 0%;
}
#index\:treehouse>details:not([open])>summary .oops-you-seem-to-have-gotten-stuck {
display: inline;
animation: 4s hello-there forwards;
}
/* Literate programming support */
:root {
--error-color: #d94141;
}
@media (prefers-color-scheme: dark) {
:root {
--error-color: #e39393;
}
}
th-literate-program[data-mode="input"] {
/* Override the cursor with an I-beam, because the editor captures clicks and does not bubble
them back up to the caller */
cursor: text;
}
th-literate-program[data-mode="output"] {
padding: 0;
background: none;
border: none;
border-radius: 0;
& iframe,
& img.placeholder-image {
border-style: none;
border-radius: 4px;
display: block;
}
& iframe {
width: 100%;
}
& img.placeholder-image.js {
transition: opacity var(--transition-duration);
}
& iframe,
& img.placeholder-image.loading {
opacity: 50%;
}
& iframe.loaded {
opacity: 100%;
}
/* The inner iframe is hidden until something requests display. */
& iframe.hidden {
display: none;
}
& pre>code {
display: block;
}
& pre.error {
color: var(--error-color);
position: relative;
&:empty {
display: none;
}
&::after {
content: 'Error';
padding: var(--8px);
position: absolute;
right: 0;
top: 0;
color: var(--text-color);
opacity: 50%;
}
}
& pre.console,
& pre.placeholder-console {
position: relative;
margin-top: 0;
margin-bottom: 0;
&:empty {
display: none;
}
&::after {
content: 'Console';
padding: var(--8px);
position: absolute;
right: 0;
top: 0;
color: var(--text-color);
opacity: 50%;
}
}
}
/* Syntax highlighting */
:root {
--syntax-comment: #9b8580;
--syntax-identifier: var(--text-color);
--syntax-keyword1: #e15e2b;
--syntax-keyword2: #199aca;
--syntax-operator: #e3755b;
--syntax-function: #d57b07;
--syntax-literal: #a64fb3;
--syntax-string: #79ac3b;
--syntax-punct: #a28680;
}
@media (prefers-color-scheme: dark) {
:root {
--syntax-comment: #aca8a4;
--syntax-identifier: var(--text-color);
--syntax-keyword1: #ffb06a;
--syntax-keyword2: #8ad4f9;
--syntax-operator: #ec9f8d;
--syntax-function: #fbd283;
--syntax-literal: #e9b9f0;
--syntax-string: #b0dd7a;
--syntax-punct: #9d9a96;
}
}
.th-syntax-highlighting span {
&.comment {
--recursive-slnt: -16.0;
color: var(--syntax-comment);
}
&.identifier {
color: var(--syntax-identifier);
}
&.keyword1 {
color: var(--syntax-keyword1);
}
&.keyword2 {
color: var(--syntax-keyword2);
}
&.operator {
color: var(--syntax-operator);
}
&.function {
color: var(--syntax-function);
}
&.literal {
color: var(--syntax-literal);
}
&.string {
color: var(--syntax-string);
}
&.punct {
color: var(--syntax-punct);
}
&.error {
color: var(--error-color);
text-decoration: wavy underline;
}
&.hidden {
display: none;
}
&.type-hint {
color: var(--syntax-comment);
font-size: 80%;
}
}
.th-syntax-highlighting {
& .export {
text-decoration: underline dotted;
cursor: help;
text-decoration-color: transparent;
transition: text-decoration-color var(--transition-duration);
}
&:hover,
&:focus {
& .export {
text-decoration-color: var(--syntax-keyword1);
}
}
}
/* Style settings sections */
section[data-cast~="settings"] {
/* Don't display settings when JavaScript is disabled.
JS overrides this value on the element itself. */
display: none;
}