Publish partially complete changes in order to make applications

This commit is contained in:
Troy 2025-04-26 16:20:40 +01:00
parent 3698e926ea
commit 4bf6f04222
Signed by: troy
GPG key ID: DFC06C02ED3B4711
184 changed files with 753 additions and 742 deletions

View file

@ -9,10 +9,28 @@ import RelatedArticles from "@components/RelatedArticles.astro";
const { article, isPost = false } = Astro.props;
const { Content } = await article.render();
const listFormatter = new Intl.ListFormat("en-GB", {
style: "long",
type: "conjunction",
});
interface NameAndUrl {
name: string;
url: string;
}
function formatNamesWithLinks(namesAndUrls: NameAndUrl[]) {
const listFormatter = new Intl.ListFormat("en-GB", {
style: "long",
type: "conjunction",
});
const linkedNames = namesAndUrls.map((item: NameAndUrl) => {
return `<a href="${item.url}" rel="nofollow" target="_blank" class="underline hover:no-underline">${item.name}</a>`;
});
return listFormatter.format(linkedNames);
}
let formattedList: string | null = null;
if (article.data.extraAuthors && article.data.extraAuthors.length !== 0) {
formattedList = formatNamesWithLinks(article.data.extraAuthors);
}
---
<Layout
@ -65,9 +83,7 @@ const listFormatter = new Intl.ListFormat("en-GB", {
article.data.extraAuthors ? (
<div class="flex items-center gap-2">
<Icon name="mdi:account-plus" />
<p title="Collaborators">
{listFormatter.format(article.data.extraAuthors)}
</p>
<p title="Collaborators" set:html={formattedList} />
</div>
) : null
}

View file

@ -42,7 +42,7 @@ const projects = [
description:
"Packard is a simple terminal based RSS aggregator meant to allow you to take a quick glance at whats occurring in topics you care about.",
tags: ["Rust", "Tokio", "Clap", "NixOS Flake"],
link: "https://code.troylusty.com/troy/packard",
link: "/projects/packard",
done: true,
},
];

View file

@ -0,0 +1,34 @@
---
import { Image } from "astro:assets";
import type { ImageMetadata } from "astro";
interface Item {
src: ImageMetadata;
alt: string;
}
interface Props {
items: Item[];
}
const { items } = Astro.props as Props;
---
<div class="grid grid-cols-1 gap-3 md:grid-cols-2">
{
items.map((item: Item) => (
<div class="aspect-[2/1] flex-col overflow-hidden rounded-sm">
{item.src && (
<a href={item.src.src} target="_blank">
<Image
src={item.src}
alt={item.alt}
loading="eager"
class="mt-0 mb-0 aspect-[2/1] h-full w-full cursor-zoom-in object-cover transition-all duration-300 ease-in-out hover:brightness-50"
/>
</a>
)}
</div>
))
}
</div>

View file

@ -1,6 +1,7 @@
---
import FormattedDate from "@components/FormattedDate.astro";
import type { CollectionEntry } from "astro:content";
import { Icon } from "astro-icon/components";
type Props = {
collection: CollectionEntry<"posts" | "projects">;
@ -19,10 +20,10 @@ const { collection } = Astro.props;
<h3 class="text-secondary mb-1 text-lg font-semibold text-nowrap">
{collection.data.title}
</h3>
<FormattedDate
date={collection.data.date}
className="text-tertiary block text-nowrap"
/>
<div class="text-tertiary flex items-center gap-2">
<Icon name="mdi:calendar" />
<FormattedDate date={collection.data.date} />
</div>
</div>
<p class="text-tertiary text-pretty">{collection.data.description}</p>
</article>

View file

@ -22,6 +22,13 @@ const { collection } = Astro.props;
fit="cover"
/>
</div>
<div
class="relative opacity-0 transition-all delay-100 duration-300 ease-in-out group-hover:opacity-100"
>
<p class="absolute right-5 bottom-5 font-medium">
{collection.data.title}
</p>
</div>
</a>
</article>
</li>

View file

@ -3,8 +3,8 @@ import { Image } from "astro:assets";
import type { CollectionEntry } from "astro:content";
interface Props {
interval?: number;
images: CollectionEntry<"projects">[];
interval?: number;
}
const { interval = 3000, images } = Astro.props;
@ -31,6 +31,11 @@ const { interval = 3000, images } = Astro.props;
class="h-full w-full rounded-sm object-cover transition-all duration-300 group-hover:brightness-50"
loading="eager"
/>
<div class="relative opacity-0 transition-all delay-100 duration-300 ease-in-out group-hover:opacity-100">
<p class="absolute right-5 bottom-5 font-medium">
{image.data.title}
</p>
</div>
</a>
</div>
))

View file

@ -59,6 +59,10 @@ export const SITE: Site = {
name: "Posts",
href: "/posts",
},
{
name: "Archive",
href: "/archive",
},
{
name: "CV",
href: "/cv",
@ -70,25 +74,6 @@ export const HOME: Metadata = {
TITLE: "Troy Lusty",
DESCRIPTION:
"Hi, my name is Troy and I'm a student 3D artist currently studying in my second year of an FdA Games and Interactive Design course in the UK.",
HOMESETTINGS: {
NUM_POSTS_ON_HOMEPAGE: 2,
NUM_PROJECTS_ON_HOMEPAGE: 6,
},
};
export const CV: Metadata = {
TITLE: "Troy Lusty",
DESCRIPTION: "Curriculum vitae.",
};
export const POSTS: Metadata = {
TITLE: "Posts",
DESCRIPTION: "A collection of articles on topics I am passionate about.",
};
export const WORK: Metadata = {
TITLE: "Work",
DESCRIPTION: "Where I have worked and what I have done.",
};
export const PROJECTS: Metadata = {
@ -96,3 +81,23 @@ export const PROJECTS: Metadata = {
DESCRIPTION:
"A collection of my projects, with links to repositories and demos.",
};
export const POSTS: Metadata = {
TITLE: "Posts",
DESCRIPTION: "A collection of articles on topics I am passionate about.",
};
export const ARCHIVE: Metadata = {
TITLE: "Archive",
DESCRIPTION: "A collection of small, unfinished, or historic personal works.",
};
export const ABOUT: Metadata = {
TITLE: "About",
DESCRIPTION: "About me.",
};
export const CV: Metadata = {
TITLE: "Troy Lusty",
DESCRIPTION: "Curriculum vitae.",
};

View file

@ -16,7 +16,14 @@ const posts = defineCollection({
alt: z.string(),
}),
tags: z.array(z.string()),
extraAuthors: z.array(z.string()).optional(),
extraAuthors: z
.array(
z.object({
name: z.string().min(1),
url: z.string().url(),
}),
)
.optional(),
categories: z.array(z.string()),
})
.merge(rssSchema),
@ -37,11 +44,18 @@ const projects = defineCollection({
alt: z.string(),
}),
tags: z.array(z.string()),
extraAuthors: z.array(z.string()).optional(),
extraAuthors: z
.array(
z.object({
name: z.string().min(1),
url: z.string().url(),
}),
)
.optional(),
categories: z.array(z.string()),
featured: z.boolean().optional(),
collection: z.boolean().optional(),
includeHero: z.boolean().optional(),
rank: z.number().positive().optional(),
})
.merge(rssSchema),
});

View file

@ -1,9 +1,9 @@
---
title: "Website"
date: 2025-04-07
date: 2025-04-25
description: "An overview of what I am using to host my digital content."
image:
url: "showcase.avif"
url: "showcase.webp"
alt: "Website showcase"
categories: ["personal"]
tags: ["self-host", "forgejo", "docker", "vps"]
@ -12,7 +12,7 @@ draft: true
This post will outline my workflow of using a self-hosted Forgejo instance and Actions runner to automatically deploy my personal site and any software releases, all without having to rely on another provider.
![Website showcase](showcase.avif)
![Website showcase](showcase.webp)
## Steps

Binary file not shown.

Before

Width:  |  Height:  |  Size: 31 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 160 KiB

View file

@ -1,22 +0,0 @@
---
title: "3D Package Design"
description: "3D Package Design inspired by the work of Derek Elliott."
date: 2020-08-16
image:
{ url: "troy-lusty-3d-package-design.avif", alt: "3D package design frame" }
tags: ["blender"]
categories: ["personal"]
---
import glowing_box_animation from "glowing-box-animation.webm";
3D Package Design inspired from [video](https://www.youtube.com/watch?v=4SRwODk0oOU) by Derek Elliott.
This was the final product from my first attempt at some simple animation within Blender done sometime in August of 2020.
<video preload="metadata" loop muted controls>
<source src={glowing_box_animation} type="video/webm" />
</video>
_Animation_
![3D package design frame](troy-lusty-3d-package-design.avif)

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 133 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 113 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 132 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 121 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 122 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 133 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 106 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 94 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.9 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.7 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.8 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 216 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 282 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 663 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.9 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 180 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.4 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 870 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.4 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 133 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 113 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 132 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 121 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 122 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 133 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 90 KiB

View file

@ -3,16 +3,15 @@ title: "A Long Way Down (Demo)"
description: "A short, atmospheric linear adventure created for my FdA Games and Interactive Design degree."
date: 2023-05-11
featured: true
image: { url: "alwd-img1.avif", alt: "A Long Way Down Intro Showcase" }
image: { url: "alwd-img1.jpg", alt: "A Long Way Down Intro Showcase" }
tags: ["unreal engine", "blender", "inkscape"]
categories: ["education"]
includeHero: true
extraAuthors: ["Sam Griffiths"]
extraAuthors: [{ name: "Sam Griffiths", url: "https://samgriffiths.dev" }]
---
import alongwaydown_demo_walkthrough from "alongwaydown-demo-walkthrough.webm";
A Long Way Down is a short, atmospheric linear adventure created alongside my friend [Sam](https://samgriffiths.dev) as a project for our FdA Games and Interactive Design degree. It is the follow up project to our previous work: [Nightmare](/projects/nightmare). Currently the [demo](https://samandtroy.itch.io/alongwaydown) is available on Itch.io.
A Long Way Down is a short, atmospheric linear adventure created alongside my friend [Sam](https://samgriffiths.dev) as a project for our FdA Games and Interactive Design degree. It is the follow up project to our previous work: [Nightmare](#nightmare), and was made to be an evolutionary improvement of it. Currently the [demo](https://samandtroy.itch.io/alongwaydown) is available to download and play on Itch.io.
<video preload="metadata" controls>
<source src={alongwaydown_demo_walkthrough} type="video/webm" />
@ -20,7 +19,7 @@ A Long Way Down is a short, atmospheric linear adventure created alongside my fr
_Demo walkthrough_
![A Long Way Down Intro Showcase](alwd-img1.avif)
![A Long Way Down Intro Showcase](alwd-img1.jpg)
_Intro_
@ -60,6 +59,26 @@ _Early environment stage_
_Initial style experiments_
### External links
## Nightmare
[Itch.io page](https://samandtroy.itch.io/alongwaydown)
import nightmare from "nightmare.webm";
This is the environment I created in collaboration with Sam Griffiths for our Unit 8 - Developing a Creative Media Production Project - Final Major Project which concluded 2021-04-21. I was in charge of the art side of the project including asset production, composition, and lighting although we both helped one another out when necessary with blueprints etc. Additionally, I created this short cinematic in Unreal Engine's cinematic level sequencer by keyframing the transform values and focus distance of a camera.
<video preload="metadata" muted controls>
<source src={nightmare} type="video/webm" />
</video>
_Environment cinematic_
![Frame 0600](troy-lusty-nightmare.avif)
_Frame 0600_
![Frame 1182](troy-lusty-nightmare-frame-1182.avif)
_Frame 1182_
![Frame 1700](troy-lusty-nightmare-frame-1700.avif)
_Frame 1700_

View file

Before

Width:  |  Height:  |  Size: 2.6 KiB

After

Width:  |  Height:  |  Size: 2.6 KiB

Before After
Before After

View file

Before

Width:  |  Height:  |  Size: 11 KiB

After

Width:  |  Height:  |  Size: 11 KiB

Before After
Before After

View file

@ -1,22 +0,0 @@
---
title: "Astronaut"
description: "Lighting and camera test."
date: 2022-03-28
image: { url: "troy-lusty-astronaut.avif", alt: "Astronaut final piece" }
tags: ["blender", "davinci resolve"]
categories: ["personal"]
---
Astronaut character lit with 1 area light using light nodes. Done to test lighting and the creation of a camera with an "anamorphic lens" inside of Blender. Final adjustments made within DaVinci Resolve including adding a lens dirt overlay by William Landgren.
![Astronaut final piece](troy-lusty-astronaut.avif)
_Astronaut Final Image_
### External links
[Domenico D&rsquo;Alisa&rsquo;s ArtStation](https://www.artstation.com/domenicodalisa)
[William Landgren&rsquo;s Instagram](https://www.instagram.com/landgrenwilliam)
[Astronaut asset](https://cubebrush.co/domenicodalisa/products/vsuspw/discovery-pay-what-you-want-2017)

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 103 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 32 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 33 KiB

View file

@ -6,12 +6,13 @@ date: 2022-10-18 # Date Persuit theme was purchased
updated: 2024-12-05
image:
{
url: "camouflage-store-barningham-raby.avif",
url: "t_pkD9Wf0QU-HD.jpg",
alt: "Camouflage Store YouTube video regarding Altberg boots comparison.",
}
tags: ["ecommerce", "shopify", "docker"]
categories: ["client work"]
featured: true
rank: 1
---
My role has me in charge of managing an [ecommerce store](https://camouflagestore.uk/) in addition to creating, editing, and publishing informational YouTube and social media content for a family run outdoors store. This includes the redesign shown below but also any maintenance and general upkeep of the site and all related systems.
@ -20,7 +21,7 @@ My role has me in charge of managing an [ecommerce store](https://camouflagestor
As of 2024-12-05 the [YouTube channel](https://www.youtube.com/@camouflagestoreuk) has 1.37k subscribers and 312,241 views over a total of 168 videos. If were to pick one video that displays the quality of the content we produce, it would probably be [SOLO ATP SAS SMOCK MK2 (2022) OVERVIEW | Camouflage Store](https://www.youtube.com/watch?v=K7wlm60rXVs). I am incredibly grateful to Steve for giving me the opportunity to continue working with him, and for the amount of creative freedom he gives me when experimenting with new ideas.
![SOLO ATP SAS SMOCK MK2 (2022) OVERVIEW | Camouflage Store YouTube Video Thumbnail](camouflage-store-video-thumbnail.avif)
![SOLO ATP SAS SMOCK MK2 (2022) OVERVIEW | Camouflage Store YouTube Video Thumbnail](K7wlm60rXVs-HD.jpg)
## Site redesign
@ -53,10 +54,3 @@ For the domain, we have gone with [camouflagestore.uk](https://camouflagestore.u
Continuing my goal of giving Steve the most amount of freedom possible without having to rely on thirdparty services, I have setup a VPS on his behalf to host a variety of services.
The first of which is an instance of [Umami](https://umami.is/), a self-hostable analytics platform. This has been hosted using Docker and includes automatic redeployments using Watchtower, and reverse proxying with Traefik.
### Other links
- [Camouflage Store](https://camouflagestore.uk)
- [YouTube](https://www.youtube.com/@camouflagestoreuk)
- [Instagram](https://www.instagram.com/camouflagestoreuk)
- [Twitter](https://twitter.com/camouflagestore)

Binary file not shown.

After

Width:  |  Height:  |  Size: 120 KiB

View file

@ -9,7 +9,6 @@ image:
}
tags: ["unreal engine", "blender", "davinci resolve", "photoshop"]
categories: ["education"]
includeHero: true
---
import deltakey from "deltakey.webm";

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.4 KiB

View file

@ -1,14 +0,0 @@
---
title: "Discord Bot"
description: "AQA Computer Science NEA project based around creating a Discord bot."
date: 2020-03-31
image: { url: "discord.avif", alt: "Discord bot" }
tags: ["python"]
categories: ["education"]
---
The objective I set myself was to write a Discord bot as my AQA Computer Science NEA Project. The program utilised [discord.py](https://github.com/Rapptz/discord.py), a Discord API wrapper for use within Python. The resulting code for the bot can be viewed in my Git repo.
### External links
https://code.troylusty.com/troy/discordbot

View file

@ -1,27 +0,0 @@
---
title: "Firespline"
description: "A fire animation test presented in a small cave scene."
date: 2022-01-06
image: { url: "troy-lusty-firespline.avif", alt: "Firespline frame" }
tags: ["blender", "davinci resolve"]
categories: ["personal"]
---
import firespline from "firespline.webm";
Cycles and DaVinci Resolve (with assets from Blend Swap and ambientCG)
This is fire animation test I did which I turned into a scene complete with reflected light on water and volumetrics.
<video preload="metadata" loop muted controls>
<source src={firespline} type="video/webm" />
</video>
_Animation_
![Firespline frame](troy-lusty-firespline.avif)
_Extracted frame_
### Assets list
https://www.blendswap.com/blend/26395, https://ambientcg.com/view?id=Rock030, https://ambientcg.com/view?id=Ground033

Binary file not shown.

Before

Width:  |  Height:  |  Size: 9.3 KiB

View file

@ -1,40 +0,0 @@
---
title: "Kikimora"
description: "A narrative driven horror game prototype done as a university project."
date: 2024-01-24
image: { url: "kikimora-titlecard.avif", alt: "Kikimora titlecard" }
tags: ["godot", "blender", "gimp", "inkscape"]
categories: ["education"]
---
import kikimora_gameplay from "kikimora-gameplay.webm";
This was my first attempt at making anything within the Godot game engine, and was consequently what resulted in me starting the creation of [MUST FIND BEANS](https://store.steampowered.com/app/3012740/MUST_FIND_BEANS/).
### Controls
WASD - Movement
CTRL - Crouch
E - Interact
Mouse - Look around
<video preload="metadata" controls>
<source src={kikimora_gameplay} type="video/webm" />
</video>
_Short gameplay video_
![Kikimora hallway screenshot](kikimora-ingame-screenshot-1.avif)
_Screenshot 1_
![Kikimora red hallway screenshot](kikimora-ingame-screenshot-2.avif)
_Screenshot 2_
### External links
[Itch.io page](https://troylusty.itch.io/kikimora)

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 13 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.3 KiB

View file

@ -5,7 +5,7 @@ date: 2021-12-11
image: { url: "troy-lusty-kraken.avif", alt: "Kraken in the Cupboard final" }
tags: ["blender"]
categories: ["personal"]
includeHero: true
featured: true
---
Rendered using Cycles X, with all compositing done inside of Blender.

View file

@ -1,6 +1,6 @@
---
title: "Logofolio"
description: "An ongoing collection of branding and logos designs."
description: "An ongoing collection of branding and logo designs."
date: 2021-06-16
image: { url: "troy-lusty-logofolio.avif", alt: "Logofolio title" }
collection: true
@ -8,12 +8,14 @@ tags: ["blender", "pixelmator", "affinity photo", "affinity designer"]
categories: ["client work"]
---
An ongoing collection of branding and logos designs. Including both 2D and 3D works created inside of various softwares and packages.
Layout inspired by: [citrus.works](https://citrus.works/)
An ongoing collection of branding and logos designs. Including both 2D and 3D works created inside of various software packages.
![Logofolio title](troy-lusty-logofolio.avif)
![Banner for juce](juce.jpg)
Rebrand for [juce](https://www.twitch.tv/juceboi).
![Header design for @_railz_](troy-lusty-logofolio-railz.avif)
Twitter header and rebrand for [railz](https://twitter.com/@_railz_). Inspired by: [Cloakzy- concept broadcast asset redesign](https://www.behance.net/gallery/100498021/Cloakzy-Concept-Broadcast-Assets)
Twitter header and rebrand for [railz](https://twitter.com/@_railz_). Inspired by [Cloakzy concept broadcast asset redesign](https://www.behance.net/gallery/100498021/Cloakzy-Concept-Broadcast-Assets).

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 MiB

View file

@ -1,21 +0,0 @@
---
title: "Megascans Artworks"
description: "A small collection of artworks made with Megascans assets."
date: 2021-01-29
collection: true
image: { url: "troy-lusty-forest-fire.avif", alt: "Forest fire" }
tags: ["quixel megascans", "blender"]
categories: ["personal"]
---
![Forest fire](troy-lusty-forest-fire.avif)
_Forest fire_
![Little Nightmares](troy-lusty-little-nightmares.avif)
_Little Nightmares_
![Crypt](troy-lusty-crypt.avif)
_Crypt_

Binary file not shown.

Before

Width:  |  Height:  |  Size: 74 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 117 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 72 KiB

View file

@ -4,48 +4,28 @@ description: "1 Corinthians 15:26 - The last enemy to be destroyed is death."
date: 2022-12-10
image:
{
url: "troy-lusty-mortis.avif",
url: "mortisupdated2_2.1.6.jpg",
alt: "Final finished artwork for Mortis project",
}
featured: true
tags: ["blender", "davinci resolve"]
categories: ["personal"]
includeHero: true
---
![Final finished artwork for Mortis project](troy-lusty-mortis.avif)
import Gallery from "@components/Gallery.astro";
_Final_
import image1 from "troy-lusty-mortis-progress-3.avif";
import image2 from "troy-lusty-mortis-progress-2.avif";
import image3 from "troy-lusty-mortis-progress-1.avif";
![Progress 3 for Mortis project](troy-lusty-mortis-progress-3.avif)
![Final finished artwork for Mortis project](mortisupdated2_2.1.6.jpg)
_Progress 3_
## Progress shots
![Progress 2 for Mortis project](troy-lusty-mortis-progress-2.avif)
_Progress 2_
![Progress 1 for Mortis project](troy-lusty-mortis-progress-1.avif)
_Progress 1_
### Assets list
- **Three D Scans**
- [Le Transi de Rene de Chalon](https://threedscans.com/musee-des-monuments-francais/le-transi-de-rene-de-chalon)
- [Font Reconstructed](https://threedscans.com/lincoln/reconstructed/)
- [Saint Hugh](https://threedscans.com/lincoln/saint-hughs/)
- [Zenobia in Chains](https://threedscans.com/saint-louis-art-museum/zenobia-in-chains/)
- **Unsplash**
- [blue red and yellow floral glass window](https://unsplash.com/photos/YEXaj7mNiCQ)
- **Textures.com**
- [Arcaded Wood Panels - PBR0716](https://www.textures.com/download/PBR0959/140830)
- [Scratches Overlay - OVL0021](https://www.textures.com/download/Overlays0025/136531)
- [Stains 7 Overlay - OVL0040](https://www.textures.com/download/Overlays0041/137435)
- [Waterplants0017](https://www.textures.com/download/Waterplants0017/14022)
- [TombHeadstone0241](https://www.textures.com/download/TombHeadstone0241/130539)
- **PolyHaven**
- [Concrete Floor 02](https://polyhaven.com/a/concrete_floor_02)
- [Large Grey Tiles](https://polyhaven.com/a/large_grey_tiles)
- **Pexels**
- [Free stock photo of 35mm, grain, texture](https://www.pexels.com/photo/35mm-film-grain-texture-246213/)
<Gallery
items={[
{ src: image1, alt: "Progress 3 for Mortis project" },
{ src: image2, alt: "Progress 2 for Mortis project" },
{ src: image3, alt: "Progress 1 for Mortis project" },
]}
/>

Binary file not shown.

After

Width:  |  Height:  |  Size: 878 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.7 KiB

View file

@ -2,14 +2,24 @@
title: "MUST FIND BEANS"
description: "What would you do if you realised your breakfast was going to be entirely free of beans, and how far would you go to make it right?"
date: 2025-05-08
updated: 2025-05-08
image: { url: "capsule.avif", alt: "MUST FIND BEANS Title Logo" }
image: { url: "main-capsule.png", alt: "MUST FIND BEANS Title Logo" }
tags: ["godot", "blender", "gimp"]
categories: ["personal"]
includeHero: true
draft: true
---
import Gallery from "@components/Gallery.astro";
import image1 from "Still2025-04-07111623_1.1.1.avif";
import image2 from "Still2025-04-07111623_1.1.6.avif";
import image3 from "Still2025-04-07111623_1.1.4.avif";
import image4 from "Still2025-04-07111623_1.1.2.avif";
import image5 from "Still2025-04-07111623_1.1.3.avif";
import image6 from "ss_8340a3c02235371547350c557fefb830e6e2d067.avif";
import image7 from "ss_c578870d1c22722983b76c3effe7fba7f5d1cb5e.avif";
import image8 from "ss_b2dc5ca65e2f24088afac3faf79f450057e13383.avif";
import image9 from "ss_3f3907ac4aa8d8e9e4ca19ecab3c51ede971b2bd.avif";
import image10 from "ss_ed538aaba4f11d33c6919a7d17657b6ffc2b422a.avif";
<div
class="border-l-4 border-orange-500 bg-orange-100 p-4 text-orange-700 dark:bg-orange-900 dark:text-orange-300"
role="alert"
@ -18,32 +28,34 @@ draft: true
<p class="m-0 mt-0 mb-0">This game is very early in development.</p>
</div>
![](capsule.avif)
![](main-capsule.png)
[MUST FIND BEANS](https://store.steampowered.com/app/3012740/MUST_FIND_BEANS/) is a fast-paced first person shooter set following the realization that you're all out of beans. The problem is, you're nearing the end of cooking all the other items and you can't just not have them. Without beans, the day just won't be started off right.
Many will try to stop you as you race out in search of the final piece of your meal. But you must not let them. Find a can of beans by any means necessary before everything else you began cooking burns.
Gameplay in MUST FIND BEANS aims to mimic games similar to the original Quake, and other modern “boomer shooters” such as ULTRAKILL, DUSK, or CRUEL. This extends not only to the fast and difficult yet predictable combat, but also the movement which has taken significant inspiration from that found within Source engine titles.
The game is not yet available but can be wishlisted on [Steam](https://store.steampowered.com/app/3012740/MUST_FIND_BEANS/) in preparation for when it releases. I was inspired to make this game after testing out Godot within a module in University for which I produced a small prototype [horror experience](https://troylusty.itch.io/kikimora).
Visuals and imagery included imitate apartment and hotel interiors within and around Miami in the 1980s. This is will be most evident though the use of a combination of brutalist architecture along with collections of interior foliage. Whilst it might not be entirely present within the presented version of the game, each “enemy” will be styled after one of the breakfast items which have been left cooking as a way to visualise the characters paranoid and overly determined mental state.
## Screenshots
## Early screenshots
<Gallery
items={[
{ src: image1, alt: "Screenshot 1" },
{ src: image2, alt: "Screenshot 2" },
{ src: image3, alt: "Screenshot 3" },
{ src: image4, alt: "Screenshot 4" },
{ src: image5, alt: "Screenshot 5" },
]}
/>
![](Still2025-04-07111623_1.1.1.avif)
![](Still2025-04-07111623_1.1.6.avif)
![](Still2025-04-07111623_1.1.4.avif)
![](Still2025-04-07111623_1.1.2.avif)
![](Still2025-04-07111623_1.1.3.avif)
### Early screenshots
## Even earlier screenshots
![](ss_8340a3c02235371547350c557fefb830e6e2d067.avif)
![](ss_c578870d1c22722983b76c3effe7fba7f5d1cb5e.avif)
![](ss_b2dc5ca65e2f24088afac3faf79f450057e13383.avif)
![](ss_3f3907ac4aa8d8e9e4ca19ecab3c51ede971b2bd.avif)
![](ss_ed538aaba4f11d33c6919a7d17657b6ffc2b422a.avif)
### External links
[Steam store page](https://store.steampowered.com/app/3012740/MUST_FIND_BEANS/)
<Gallery
items={[
{ src: image6, alt: "Screenshot 6" },
{ src: image7, alt: "Screenshot 7" },
{ src: image8, alt: "Screenshot 8" },
{ src: image9, alt: "Screenshot 9" },
{ src: image10, alt: "Screenshot 10" },
]}
/>

Binary file not shown.

After

Width:  |  Height:  |  Size: 72 KiB

View file

@ -1,37 +0,0 @@
---
title: "Nightmare"
description: "Little Nightmares inspired game demo and environment completed for my college final major project."
date: 2021-04-21
image: { url: "troy-lusty-nightmare.avif", alt: "Nightmare Frame 0600" }
tags: ["unreal engine", "blender", "davinci resolve", "photoshop", "zbrush"]
categories: ["education"]
extraAuthors: ["Sam Griffiths"]
---
import nightmare from "nightmare.webm";
This is the environment I created in collaboration with Sam Griffiths for our Unit 8 - Developing a Creative Media Production Project - Final Major Project. I was in charge of the art side of the project including asset production, composition, and lighting although we both helped one another out when necessary with blueprints etc. Additionally, I created this short cinematic in Unreal Engine's cinematic level sequencer by keyframing the transform values and focus distance of a camera.
_IMPORTANT: I would just like to add that since we were taking heavy inspiration from both Little Nightmares and INSIDE, combined with the relatively short time window we had to create the playable demo in, we decided to take the main character model and player animations from Little Nightmares and put them into our project. This allowed for us to much more easily create the environment around the character's scale emphasising their small size in comparison to the surroundings._
<video preload="metadata" muted controls>
<source src={nightmare} type="video/webm" />
</video>
_Environment cinematic_
![Frame 0600](troy-lusty-nightmare.avif)
_Frame 0600_
![Frame 1182](troy-lusty-nightmare-frame-1182.avif)
_Frame 1182_
![Frame 1700](troy-lusty-nightmare-frame-1700.avif)
_Frame 1700_
### External links
[Sam's ArtStation post](https://www.artstation.com/artwork/rA1yyE)

View file

@ -9,7 +9,7 @@ categories: ["personal"]
![Packard GitHub v0.0.1 Release](packard.avif)
Packard is a simple RSS aggregator meant to allow you to take a quick glance at what's occurring in topics you care about. This is my first attempt at making something with Rust so that I may learn alongside creating something that I personally find useful.
[Packard](https://code.troylusty.com/troy/packard) is a simple RSS aggregator meant to allow you to take a quick glance at what's occurring in topics you care about. This is my first attempt at making something with Rust so that I may learn alongside creating something that I personally find useful.
![Demo](demo.gif)
@ -76,7 +76,3 @@ news = [
After running Packard with your configured settings, the parsed results can be opened in your default browser however your terminal allows for opening URLs. For example the keybind for this with [Foot](https://codeberg.org/dnkl/foot#urls) is `ctrl` + `shift` + `o`.
Currently no keyboard interaction is implemented. To get around this you can pipe the output of Packard into a tool like `less` like so: `packard -c 12 -l news -s 3 | less`.
### External links
https://code.troylusty.com/troy/packard

View file

@ -9,7 +9,7 @@ image:
}
categories: ["personal"]
tags: ["blender", "davinci resolve", "gimp", "inkscape", "krita"]
includeHero: true
featured: true
---
![Final piece of Pasikdhar project](troy-lusty-pasikdhar-final.avif)

View file

@ -6,7 +6,7 @@ updated: 2024-12-12
image: { url: "sinkie-soldiers.avif", alt: "Sinkie Soldiers Logo" }
categories: ["personal"]
tags: ["unreal engine", "blender", "gimp", "fl studio"]
extraAuthors: ["Sam Griffiths"]
extraAuthors: [{ name: "Sam Griffiths", url: "https://samgriffiths.dev" }]
---
**This project was previously only a game jam submission but very soon it will be polished up and published onto [Steam](https://store.steampowered.com/app/3368860/Sinkie_Soldiers)!**

View file

@ -10,6 +10,7 @@ image:
}
tags: ["photoshop", "after effects"]
categories: ["education"]
featured: true
---
import climate_emergency_exhibition from "climate-emergency-exhibition.webm";

View file

@ -1,160 +0,0 @@
---
title: "Smaller personal projects"
description: "A collection of smaller personal projects."
date: 2023-10-12
updated: 2023-11-23
collection: true
featured: true
image:
{ url: "troy-lusty-personal-23-11-2023.avif", alt: "Marble statue render" }
categories: ["personal"]
tags:
["blender", "photoshop", "affinity photo", "davinci resolve", "unreal engine"]
includeHero: true
---
import interior_test from "interior_test.webm";
import cinematic_lighting_in_blender from "cinematic-lighting-in-blender-night-lighting-03-projection.webm";
import abstract_chrome_loop from "abstract-chrome-loop.webm";
import houdini_pillows from "houdini-pillows.webm";
import houdini_abstract_particles from "houdini-abstract-particles.webm";
import houdini_fabric_hoses from "houdini-fabric-hoses.webm";
import plastic_bag_exhibition_test from "plastic-bag-exhibition-test.webm";
import krampus_unrealengine4_learning from "krampus-unrealengine4-learning.webm";
import playstation_motion_graphics_loop from "playstation-motion-graphics-loop.webm";
This is an ongoing collection of smaller personal project artwork renders that I have created in my free time using Blender. I am constantly updating this collection. **Started 26th Feb 2021.**
![2023-11-23](troy-lusty-personal-23-11-2023.avif)
_23-11-2023 Cycles with AgX. [3D model](https://www.myminifactory.com/object/3d-print-ugolino-and-his-sons-268545) and [Marble textures](https://www.textures.com/download/PBR0494/138505)_
![2023-11-02](troy-lusty-personal-02-11-2023.avif)
_02-11-2023 Cycles._
![12-10-2023](troy-lusty-personal-12-10-2023.avif)
_12-10-2023 Cycles. [Unsplash](https://unsplash.com/photos/79RV1Tnnrc0)_
<video preload="metadata" loop muted controls>
<source src={interior_test} type="video/webm" />
</video>
_19-07-2023 Cycles_
<video preload="metadata" loop muted controls>
<source src={cinematic_lighting_in_blender} type="video/webm" />
</video>
_08-04-2023 Cycles - Watch [Night Lighting 03](https://www.blendermarket.com/products/cinematic-lighting-in-blender). [Sony TC-510-2 Tape Recorder - by Dolgov](https://sketchfab.com/3d-models/sony-tc-510-2-tape-recorder-32acbe50ba0f4abc99af88e0d76f28f9)_
![18-04-2023](troy-lusty-personal-18-04-2023.avif)
_18-04-2023 Cycles_
<video preload="metadata" loop muted controls>
<source src={abstract_chrome_loop} type="video/webm" />
</video>
_06-04-2022 Eevee and DaVinci Resolve_
<video preload="metadata" loop muted controls>
<source src={houdini_pillows} type="video/webm" />
</video>
_08-02-2023 Houdini and Cycles_
<video preload="metadata" loop muted controls>
<source src={houdini_abstract_particles} type="video/webm" />
</video>
_UNSURE Houdini and Cycles_
<video preload="metadata" loop muted controls>
<source src={houdini_fabric_hoses} type="video/webm" />
</video>
_UNSURE Houdini and Cycles_
<video preload="metadata" loop muted controls>
<source src={plastic_bag_exhibition_test} type="video/webm" />
</video>
_UNSURE Cycles_
![27-12-2022](troy-lusty-personal-27-12-2022.avif)
_27-12-2022 Cycles_
![30-10-2022](troy-lusty-personal-30-10-2022.avif)
_30-10-2022 Cycles X (https://www.textures.com/download/PBR0821/139423 and engin-akyurt-9mIV0FR9uzo-unsplash)_
![06-10-2022](troy-lusty-personal-06-10-2022.avif)
_06-10-2022 Cycles X (https://avopix.com/photo/59076-35mm-film-grain-texture)_
![26-09-2022](troy-lusty-personal-26-09-2022.avif)
_26-09-2022 Cycles X Inspired by the work of Wes Cockx: https://cream3d.com_
![17-05-2022](troy-lusty-personal-17-05-2022.avif)
<video preload="metadata" loop muted controls>
<source src={krampus_unrealengine4_learning} type="video/webm" />
</video>
_UNSURE Unreal Engine 4_
_17-05-2022 Cycles X (https://avopix.com/photo/59076-35mm-film-grain-texture)_
![27-03-2022](troy-lusty-personal-27-03-2022.avif)
_27-03-2022 Cycles X (https://unsplash.com/photos/T-SDVHQUcgc, https://polyhaven.com/a/cobblestone_05, https://polyhaven.com/a/castle_brick_07)_
![21-02-2022](troy-lusty-personal-21-02-2022.avif)
_21-02-2022 Cycles X ([Rocks](https://www.blenderkit.com/asset-gallery?search_text=rock&query=category_subtree%3Alandscape%2Bis_free%3Atrue+order%3A_score), [Film grain texture](https://avopix.com/photo/59076-35mm-film-grain-texture), and [Moon texture](https://svs.gsfc.nasa.gov/4720))_
![15-01-2022](troy-lusty-personal-15-01-2022.avif)
_15-01-2022 Cycles X (with assets from https://ambientcg.com and https://blendswap.com/blend/20990)_
<video preload="metadata" loop muted controls>
<source src={playstation_motion_graphics_loop} type="video/webm" />
</video>
_17-09-2021 Eevee_
![10-07-2021](troy-lusty-personal-10-07-2021.avif)
_10-07-2021 Cycles and Affinity Photo (with assets from Chocofur)_
![16-05-2021](troy-lusty-personal-16-05-2021.avif)
_16-05-2021 Cycles and Affinity Photo_
![17-04-2021](troy-lusty-personal-17-04-2021.avif)
_17-04-2021 Cycles and Photoshop_
![16-03-2021](troy-lusty-personal-16-03-2021.avif)
_16-03-2021 (Updated on 21-03-2021) Cycles and Photoshop Inspired by: https://www.artstation.com/artwork/dONbew_
![25-02-2021](troy-lusty-personal-25-02-2021.avif)
_25-02-2021 (Updated on 17-03-2021) Cycles and Photoshop (with assets from Ian Hubert, Sketchfab and Graswald) https://sketchfab.com/3d-models/ehrengrab-rudolf-von-alt-8ec85f8c2b73443d9f7da539b79fdf42_
![23-01-2021](troy-lusty-personal-23-01-2021.avif)
_23-01-2021 (Fixed 12-01-2022) Eevee and Photoshop (with an asset from Sketchfab) https://sketchfab.com/3d-models/fiaker-denkmal-9b919637405e4e31af2e652a5f6ceb41_
![20-01-2021](troy-lusty-personal-20-01-2021.avif)
_20-01-2021 Cycles_
![15-01-2021](troy-lusty-personal-15-01-2021.avif)
_15/01/2021 Cycles_

Binary file not shown.

Before

Width:  |  Height:  |  Size: 54 KiB

Some files were not shown because too many files have changed in this diff Show more