← Fantasy3D assetfogon/flores-luminosas
Flores luminosas
Drag to turn it// «Flores luminosas» · gpt-6-sol (medium)
// A patch of magical glowing flowers: several tall thin stems with bell-shaped flowers glowing cyan, pink and lime, on a little mound of dark grass with tiny glowing dots floating around.
// A mossy little island for the flowers to grow from.
ellipsoid(24, 24, 1, 19, 16, 5, "#343d3c");
ellipsoid(24, 24, 2, 18, 15, 4, "#354a3e");
forEach((x, y, z, color) => {
if (get(x, y, z + 1) !== undefined) return;
const grass = rand();
set(x, y, z,
grass < 0.16 ? "#607d60" :
grass < 0.43 ? "#486b52" : "#395847");
if (rand() < 0.055 && z >= 3)
set(x, y, z + 1, rand() < 0.5 ? "#78966b" : "#587d64");
});
// Pebbles and tiny luminous mushrooms among the grass.
for (const [x, y, z] of [[8, 24, 2], [37, 35, 2], [30, 10, 3], [17, 37, 2]]) {
ellipsoid(x, y, z, 2, 1, 1, "#68716a");
set(x, y - 1, z, "#929b8a");
}
for (const [x, y, z, cap] of [
[10, 29, 4, "#e579c9"], [36, 18, 4, "#72ded0"],
[20, 36, 5, "#dc8acb"]
]) {
box(x, y, z, x, y, z + 2, "#d7d4b5");
ellipsoid(x, y, z + 3, 2, 2, 1, cap);
set(x, y - 2, z + 3, "#fff3da");
}
// Root position, center of the hanging bell, lowest petal, and bloom colors.
const flowers = [
{ root: [12, 17], head: [11, 14], b: 26, petals: ["#13b7cf", "#36e9ed", "#a4ffff"] },
{ root: [23, 21], head: [24, 18], b: 30, petals: ["#b940a5", "#f56acb", "#ffd0f3"] },
{ root: [35, 17], head: [35, 14], b: 27, petals: ["#8ac638", "#c2f65b", "#edffaf"] },
{ root: [15, 32], head: [13, 34], b: 24, petals: ["#a847bd", "#ed7add", "#ffcaef"] },
{ root: [29, 32], head: [29, 34], b: 28, petals: ["#149fa4", "#54eeee", "#b7ffff"] },
{ root: [38, 27], head: [39, 28], b: 23, petals: ["#82b937", "#bcf65d", "#efffaa"] }
];
for (const f of flowers) {
const [rx, ry] = f.root;
const [hx, hy] = f.head;
const top = f.b + 8;
// Thin, gently arched stems with a brighter side.
line(rx, ry, 5, rx, ry, top + 1, 0, "#346e61");
line(rx + 1, ry, 6, rx + 1, ry, top - 4, 0, "#57a282");
line(rx, ry, top + 1, hx, hy, top + 2, 0, "#438d73");
line(hx, hy, top + 2, hx, hy, top - 1, 0, "#68b394");
// Paired broad leaves, reaching away from each stem.
for (const [side, height] of [[-1, 11], [1, 16]]) {
const lx = rx + side * 4;
line(rx, ry, height, lx, ry + 1, height + 2, 0, "#43876b");
ellipsoid(lx, ry + 1, height + 2, 3, 1, 1, "#467f65");
line(rx + side, ry, height + 1, lx + side, ry + 1, height + 2, 0, "#79b990");
}
box(rx, ry, 5, rx + 1, ry + 1, 7, "#385f50");
}
// Little motes suspended between the stems, placed before the animated heads.
for (let i = 0; i < 39; i++) {
const x = Math.round(7 + rand() * 34);
const y = Math.round(9 + rand() * 30);
const z = Math.round(9 + rand() * 28);
if (get(x, y, z) !== undefined) continue;
const tint = ["#4cefee", "#ff81df", "#d4ff6c"][i % 3];
set(x, y, z, tint);
if (i % 5 === 0 && get(x, y, z + 1) === undefined)
set(x, y, z + 1, "#eafff1");
}
// One animated part holds every luminous bell.
part("flowerHeads", [24, 24, 29]);
for (const f of flowers) {
const [hx, hy] = f.head;
const radii = [4.2, 5.0, 4.8, 4.3, 3.6, 2.9, 2.2, 1.5, 0.9];
const hollow = [2.7, 2.5, 2.0, 1.4, 0.7];
for (let level = 0; level < radii.length; level++) {
for (let dx = -6; dx <= 6; dx++) {
for (let dy = -6; dy <= 6; dy++) {
const distance = Math.hypot(dx, dy);
const scallop = 0.35 * Math.cos(4 * Math.atan2(dy, dx));
if (distance > radii[level] + scallop) continue;
if (level < hollow.length && distance < hollow[level]) continue;
const edge = distance > radii[level] - 0.85;
const shade = level <= 1 ? 2 : edge ? 1 : level >= 6 ? 2 : 0;
set(hx + dx, hy + dy, f.b + level, f.petals[shade]);
}
}
}
// Four soft petal tips make the open, downward-facing rim unmistakable.
for (const [dx, dy] of [[4, 0], [-4, 0], [0, 4], [0, -4]]) {
set(hx + dx, hy + dy, f.b - 1, f.petals[1]);
set(hx + dx, hy + dy, f.b, f.petals[2]);
}
// Bright stamens peek out from inside the bell.
set(hx, hy, f.b + 2, f.petals[2]);
set(hx, hy, f.b + 1, "#fffcea");
set(hx - 1, hy, f.b + 1, f.petals[2]);
set(hx + 1, hy, f.b + 1, f.petals[2]);
}
animate("flowerHeads", {
type: "colors",
palette: ["#31f8ff", "#ff69cf", "#c6ff50", "#f2ffff"],
pattern: "wave",
glow: 0.9
});import { draw } from "./assets/voxel";
import { floresLuminosas } from "./assets/flores-luminosas";
// Every frame: standing on (x, y), the centre of its base.
draw(ctx, floresLuminosas, x, y, { size: 64, angle: 0, t: performance.now() / 1000 });
// size: its longest side, in px
// angle: turn on the floor, in radians
// t: seconds; if it moves, that animates it# In a terminal, in the game's folder
fogon assets add flores-luminosas
# With Fogón's tools (connector)
add_assets({ slug: "<your-game>", ids: ["flores-luminosas"] })
# It lands in client/assets/flores-luminosas.ts
# https://fogon.page/object/flores-luminosas