Website update: code blocks, search, lightbox and more!
Published: 2023-06-24 19:19:18

---
title: Website update: code blocks, search, lightbox and more!
published: true
date: 2023-06-18 17:13:45 UTC
tags: 
canonical_url: https://felixrunquist.com/posts/a-website-update
cover_image: https://felixrunquist.com/api/get-image?image=%2Fwp-content%2Fuploads%2F2023%2F06%2Fsite-redesign.png&w=3840&q=75
---

Since I got my website to a relative production-ready stage last year, I wanted to release an update to my website to work on a few much-needed improvements.

## Revamped post experience

I’ve always felt like my posts layout has felt pretty bland, which doesn’t integrate with the rest of my website design. I started off building my website from Next.js’ [WordPress example](https://github.com/vercel/next.js/tree/canary/examples/cms-wordpress), which, although modern in its design, is very minimal. I decided to add a few features to build on my existing content:

### Code blocks

As I constantly write posts about programming, code blocks are an elemental part of my posts. The code blocks I started off with use [Prism.js](https://prismjs.com/), however I knew from the beginning that this was a temporary solution. While it does support a lot of languages for syntax highlighting, it lacks support for things such as file trees, and interactive code playgrounds. A package that has been [all](https://www.joshwcomeau.com/react/next-level-playground/) [the](https://blog.maximeheckel.com/design/) [rave](https://bestofjs.org/projects/sandpack) in the dev environment as of late is [Sandpack](https://sandpack.codesandbox.io/) by CodeSandbox. It’s a Javascript-oriented playground that features the same in-browser bundler used on CodeSandbox for running client-side node.js. It’s very performant and has excellent code formatting and file tree support. The only thing it lacks is support for languages other than Javascript, say if you want to use it not for the previews but just for code blocks.

![Image description](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/zpcg7khxuajgxmnowyb6.png)

### Full-bleed images and lightbox

Most online reading experiences feature _full-bleed_ images, meaning that images in a post expand to the size of the browser content while the text remains within its container (it’s not a good practice to have text span across wide screens as it makes it hard to read). I implemented a CSS class for these kind of images.

![](https://felixrunquist.com/api/get-image?image=/wp-content/uploads/2023/06/Artboard.png)

Another feature on sites such as Medium is that one can click on images in a post to expand them. This is called a Lightbox. You can test out the Lightbox functionality on my website at [the original article](https://felixrunquist.com/posts/a-website-update).

### Post headers

Something I didn’t like with Next.js’ wordpress example is the look of posts. Everything is huge, and while that might be the look they are going for, it’s tiring having to scroll everywhere. For instance, the cover image is positioned under the fold, which means that a visitor needs to scroll before deciding if they want to read the post based on the title and cover image. I decided on a responsive design to make sure the cover image is above the fold on all devices.

![](https://felixrunquist.com/api/get-image?image=/wp-content/uploads/2023/06/chrome-1024x679.png)
_Next.js’ blog example with cover image under the fold_

![](https://felixrunquist.com/api/get-image?image=/wp-content/uploads/2023/06/Chrome-2-1024x644.png)
_My updated design_

I also decided to include small flourishes such as drop caps, which felt authentic to my design.

### Post categories and search

Something I’ve wanted to do from day one is to implement a post search feature. I initially thought it would be quite time consuming, with hacky `fetch`es and asynchronous calls to my CMS, but I realized that I could do all the searches client-side with Kent C. Dodd’s `match-sorter` package. I also wanted to make post categories visible to users. Since they are already implemented in the CMS I use (WordPress) I only had to do half the work and implement it client-side. Since I have a lot of whitespace, I found a space for my search bar and categories elements.

![](https://felixrunquist.com/api/get-image?image=/wp-content/uploads/2023/06/Screenshot-2023-06-10-at-9.19.47-PM-1024x894.png)
_The search bar being used_

![](https://felixrunquist.com/api/get-image?image=/wp-content/uploads/2023/06/Screenshot-2023-06-10-at-9.20.43-PM-1024x957.png)
_Categories being displayed_

## Header and footer

I wasn’t very happy with the header transition I have – as you scroll and it collapses, it’s always felt a little jittery. I replaced my trigger-based animation (i.e. when you scroll past a certain point, the size transitions) with a scroll-based animation (i.e. the scroll controls the animation progress). Here’s the difference:

 /App.js:
```
import ‘./styles.css’
import { useState, useEffect } from ‘react’
export default function App(){
const [expanded, setExpanded] = useState(true);
useEffect(() =&gt; {
document.addEventListener(‘scroll’, scroll)
return ()=&gt;{
  document.removeEventListener(‘scroll’, scroll)
}
},[])
function scroll(){
setExpanded(window.scrollY &lt;= 50)
}
return (
<div classname="container">
  <div classname="{'header'" expanded :>
    <h1>Header </h1>
    <p>{expanded ? ‘Expanded’ : ‘Collapsed’}</p>
  </div>
</div>
)
}
```
/styles.css: 
```
body {margin: 0; }
* {font-family: sans-serif; }
.container {width: 100%; height: 200%; height: 200vh; }
.header {width: 100%; height: 4rem; background: #8CC0DE; transition: height .3s ease-out; position: fixed; }
.header p, .header h1 {margin: .5rem 0; display: inline-block; }
.header.expanded {height: 8rem; }
```
Trigger-based animation

/App.js: 
```
import ‘./styles.css’
import { useState, useEffect } from ‘react’
export default function App(){
const [progress, setProgress] = useState(0);
useEffect(() =&gt; {
document.addEventListener(‘scroll’, scroll)
return ()=&gt;{
  document.removeEventListener(‘scroll’, scroll)
}
},[])
function scroll(){
setProgress(Math.max(Math.min(window.scrollY / 50, 1), 0))
}
return (
<div classname="container">
  <div classname="{'header'}" style="{{'--progress':" progress>
    <h1>Header </h1>
    <p>Progress: {progress}</p>
  </div>
</div>
)
}
```
styles.css: 
```
body {margin: 0; }
* {font-family: sans-serif; }
.container {width: 100%; height: 200%; height: 200vh; }
.header {width: 100%; height: 4rem; background: #8CC0DE; position: fixed; }
.header p, .header h1 {margin: .5rem 0; display: inline-block; }
.header {height: calc((1 – var(—progress)) * 8rem + var(—progress) * 4rem); }

```
Scroll-based animation

Notice how in the first example, the header stays expanded, right until you scroll past a certain point? The scroll-based animation feels much more responsive as it adapts to your scrolling speed.

When it comes to the footer, I never got to finishing it. I spent time positioning the links to social media and other items I wanted to feature.

![](https://felixrunquist.com/api/get-image?image=/wp-content/uploads/2023/06/Screenshot-2023-06-11-at-2.33.21-PM-1024x498.png)

## Design

To make the colors and fonts I use on this website easily retrievable, I made a design page which groups common elements. You can find the page [here](https://felixrunquist.com/design).

![](https://felixrunquist.com/api/get-image?image=/wp-content/uploads/2023/06/Screenshot-2023-06-17-at-5.43.35-PM-1024x457.png)
_A few elements featured on my design page_

## A never-ending journey

I believe a website is never fully finished, and there are always tweaks that can be made. I’ve compiled a list of things I’d like to change, and you can track my progress [here](https://felixrunquist.com/roadmap). As a bit of fun, I wanted to explore the current trend that are [bento grids](https://bentogrids.com/) and create one featuring everything I’ve changed as part of the redesign.

![](https://felixrunquist.com/img/bento-redesign.png)

This article was retrieved from [felixrunquist.com](https://felixrunquist.com)