(I make websites.)
THIS IS ME NOW
THIS WAS ME THEN
We have this legacy software platform, which was built in Ruby on Rails, and has a lot of problems, both visually and with general reliability.
We want to rebuild this entire platform in .NET, and we have the backend part of it figured out, but we need somebody to do the frontend, hopefully very quickly.
The Client
We need a new website!
The Client
Okay, that means we need a framework.
Jeff
† this framework is deprecated
div { width: ...; }
code | Result |
---|---|
500px |
500 pixels wide |
50% |
50% of the container |
66em |
66 letters current font size |
66rem |
66 letters base font size |
1fr | 1 fraction of the remaining width this is grid-specific |
50vw | 50% of the viewport width |
50vh | 50% of the viewport height |
We like that Apple design where the whole screen is just a single slide and then when you scroll down you see another slide.
The Client
Okay, let's write a bunch of javascript to make that work
Jeff
ㅤㅤ...
ㅤㅤ...
ㅤㅤ...
main {
ㅤsection { min-height: 100vh; }
}
section {
ㅤdisplay: flex; align-items:center; justify-content:center;
}
main { scroll-snap-type: y proximity; }
section {
ㅤdisplay: flex; align-items:center; justify-content:center;
ㅤscroll-snap-align: start;
}
Okay, that's nice, but now I want the sections to have backgrounds, but the background should move separately from the foreground, and also put a gradient in there.
kthxbye!
The Client
Parallax!? We need javascript for that!
Jeff
main { scroll-snap-type: y proximity; }
section {
ㅤmin-height: 100vh;
ㅤdisplay: flex; align-items:center; justify-content:center;
ㅤscroll-snap-align: start;
ㅤalign-items:center;
}
main { scroll-snap-type: y proximity; }
section {
ㅤmin-height: 100vh;
ㅤㅤdisplay: flex; justify-content:center;
ㅤscroll-snap-align: start;
ㅤalign-items: flex-end;
ㅤbackground-attachment: fixed;
ㅤbackground-size:cover; background-position: center;
ㅤ.content { position: relative;
ㅤㅤ&:before { content:'';
ㅤㅤㅤposition:absolute; top:0; bottom:0; right:0; left:0;
ㅤㅤㅤbackground:linear-gradient(rgba(0,0,0,0), rgba(0,0,0,0.95));
ㅤㅤ}
ㅤ}
}
ㅤㅤ
ㅤㅤㅤㅤ
ㅤㅤㅤㅤㅤㅤ
ㅤㅤㅤㅤㅤㅤㅤㅤ...
ㅤㅤㅤㅤㅤㅤ
ㅤㅤㅤㅤ
ㅤㅤ
We need to build a brand new website. It's gonna have a topnav and then we have to have a side rail as well because we have a lot of content, and obviously a footer.
The Client
A whole site layout? We're gonna need a framework for that!
Jeff
ㅤ...
ㅤ...
ㅤ...
ㅤ
.layout { display:grid; grid-template-columns: 260px 1fr;
ㅤheader, footer { grid-column: span 2 ; }
}
.layout {
ㅤdisplay:grid;
ㅤgrid-template-columns: 260px 1fr;
ㅤgrid-template-areas:
ㅤㅤ"header header"
ㅤㅤ"aside main"
ㅤㅤ"footer footer";
ㅤheader { grid-area: header; }
ㅤaside { grid-area: aside; }
ㅤmain { grid-area: main; }
ㅤfooter { grid-area: footer; }
}
Thanks for the website layout! Okay, now we have to have a page with a bunch of blog teasers. We're gonna show an image and the headline and some tags, probably some other stuff too, and we don't know how many there's gonna be.
Oh, and obviously it has to be responsive for all screensizes.
The Client
Let's see which frontend framework will work with this.
Jeff
ㅤ...
ㅤ...
ㅤ...
ㅤ...
.cards { display: grid; row-gap:60px; column-gap:10px;
ㅤ@media (min-width: 980px) { grid-template-columns: repeat(3,1fr); }
ㅤ@media (max-width: 979px) { grid-template-columns: repeat(2,1fr); }
ㅤ@media (max-width: 580px) { grid-template-columns: repeat(1,1fr); }
ㅤ.card { display:grid; grid-template-columns: 1fr; gap:$padding; }
}
.card { display:grid; gap:$padding;
ㅤgrid-template-columns: 1fr;
ㅤ.headline { font-size:1.15rem; }
ㅤfigure { margin-top:-2em; }
}
.card { display:grid; gap:$padding;
ㅤ@media (min-width:$min-width) {
ㅤㅤgrid-template-columns: 1fr;
ㅤㅤ.headline { font-size:1.15rem; }
ㅤㅤfigure { margin-top:-2em; }
ㅤ}
ㅤ@media (min-width:$alt-card-min) and (max-width: $alt-card-max) {
ㅤㅤgrid-template-columns: 210px 1fr 160px;
ㅤㅤ.headline { font-size:clamp(1rem,4.5vw,1.7rem); }
ㅤㅤ// ㅤㅤㅤㅤㅤㅤㅤㅤㅤㅤ ☝️ we'll get back to this one.
ㅤㅤfigure { margin-left: -20px; margin-top:unset; grid-row: span 2; }
ㅤㅤ.headline, .author { grid-column: span 2; }
ㅤㅤ.summary { grid-column: span 3; }
ㅤㅤ.tags { grid-column: span 2; }
ㅤ}
}
Nearly there! We really like it, but...
We want to alternate every other card, so the first one image on the left headline on the right. Second one, image on the right headline on the left.
Oh but also? Every other card, we actually want to swap around the author and dates?
I WILL NOT EXPLAIN MY REASONS 😡
kthxbye!
The Client
.card:nth-child(even) { grid-template-columns: 1fr 210px;
ㅤ.headline { order: 1; }
ㅤfigure { order: 2; margin-right:-20px; }
ㅤ.publish-date { order: 3; }
ㅤ.summary { order: 4; }
ㅤ.tags { order: 5; }
ㅤ.author { order: 6; }
}
Hmmmmmmm, I just realized, all of these are links, but we don't have any hover action in there.
Okay, so we want it where when you hover on the image, the title goes orange, but also? The card gets bigger, and it goes up a bit?
.card {
ㅤtransform: all 0.3s ease;
ㅤ&:hover {
ㅤㅤmargin-top:-20px; margin-left:-20px; margin-right:-20px;
ㅤ}
}
transform
.card:hover { transform:... }
transform: translateX($x);
transform: translateY($y);
transform: translateZ($z);
transform: translate($x,$y);
transform: translate3d($x,$y,$z);
transform: scale($amount);
transform: scale($x,$y);
transform: scale3d($x,$y,$z);
transform: rotate($degrees);
transform: skew($angleX,$angleY);
transform: perspective($amount);
transform: matrix($a, $b, $c, $d, $tx, $ty)
.card {
ㅤtransition: box-shadow 0.3s linear, transform 0.3s ease;
ㅤ&:hover {
ㅤㅤbox-shadow: $card-shadow;
ㅤㅤtransform: scale(1.08) translateY(-8%); z-index: $z-topcard;
ㅤ}
}
font-size: clamp($min,$baseline,$max);
article {
.inner { font-size: clamp(16px, 2.4vw, 22px);
max-width: 66ch; margin-left:auto; margin-right:auto;
h1 { font-size: clamp(32px, 4.7vw, 76px); }
h2 { font-size: clamp(26px, 3.8vw, 66px); }
h3 { font-size: clamp(18px, 3vw, 56px); }
h1, h2, h3 { font-weight:$bold; font-family:$headline-font; }
}
}
ㅤ
fieldset {
ㅤdisplay:grid; grid-template-columns: 1fr;
ㅤinput, select { border:3px solid $form-inactive; order:2; }
ㅤlabel { order: 1; }
ㅤ&:hover {
ㅤㅤlabel { color:$blue; }
ㅤㅤinput, select { border-color:$form-active; }
ㅤ}
ㅤinput, select {
ㅤㅤ&:focus { border-color: $form-active;
ㅤㅤㅤ~ label { color:$form-active; }
ㅤㅤ}
ㅤ}
}
iframe {
ㅤaspect-ratio: 16/9;
}
.content-with-rail { display:grid; grid-template-columns: 1fr 200px;
ㅤ.rail-holder { position: relative;
ㅤㅤ.rail { position:sticky: top:$gap; }
ㅤ}
}
.parallelogram {
ㅤclip-path: polygon(0 20%, 100% 0%, 100% 80%, 0% 100%);
}
.ellipse {
ㅤclip-path: ellipse(50% 25% at 50% 50%);
}
.inset {
ㅤclip-path: inset(5% 20% 15% 10%);
}
.heart {
ㅤclip-path: path('M213.1,6.7c-32.4-14.4-73.7,0-88.1,30.6C110.6,4.9,67.5-9.5,36.9,6.7C2.8,22.9-13.4,62.4,13.5,110.9 C33.3,145.1,67.5,170.3,125,217c59.3-46.7,93.5-71.9,111.5-106.1C263.4,64.2,247.2,22.9,213.1,6.7z');
}
.notch-right {
ㅤfloat:right; margin-left:1em; margin-bottom:1em;
ㅤshape-outside: polygon(100% 0, 0 0, 100% 100%);
}
.notch-left {
ㅤfloat:left; margin-right:1em; margin-bottom:1em;
ㅤshape-outside: polygon(100% 0, 0 0, 0 100%);
}
.ellipse-left {
ㅤfloat:left; padding-right:1em;
ㅤshape-outside: ellipse();
}
lemon@ahoylemon.xyz | |
[deprecated] | |
@ahoylemon@mastodon.social | |
Sessionize.com/lemon | |
github.com/AhoyLemon | |
![]() |
Find me, I'm around. |
Wish I could be there.
Maybe next time?
Questions?