← Fantasy3D assetfogon/hechicera
Hechicera
Drag to turn it// «Hechicera» · gpt-6-sol (medium)
// A cartoon sorceress facing front (-y): long dark purple hair, a deep violet dress with gold trim and a high collar, a short magenta cape, and both hands raised in front holding a floating ball of swirling magenta-violet magic energy.
const violet = "#48216f";
const violetLight = "#693295";
const violetDark = "#2d164e";
const gold = "#eabf65";
const goldLight = "#ffe49a";
const hair = "#26112f";
const hairLight = "#48224f";
const skin = "#efbba5";
// Short magenta cape, spreading behind the shoulders.
for (let z = 16; z <= 29; z++) {
const w = 10 - (z - 16) * 0.19;
for (let x = Math.ceil(24 - w); x <= Math.floor(24 + w); x++) {
const edge = Math.abs(x - 24) / w;
const front = Math.round(29 + edge * 2);
const back = Math.round(34 - edge);
for (let y = front; y <= back; y++) {
const c = z < 18 ? "#f07cb7"
: x < 19 ? "#a83683"
: y === back ? "#79265f"
: "#c44799";
set(x, y, z, c);
}
}
}
line(15, 31, 28, 33, 31, 28, 1, "#f291c2");
// Long hair behind the head and down over the cape.
ellipsoid(24, 25, 32, 8, 7, 11, hair);
ellipsoid(17, 27, 24, 3, 4, 8, hair);
ellipsoid(31, 27, 24, 3, 4, 8, hair);
ellipsoid(16, 25, 20, 2, 3, 5, "#34173e");
ellipsoid(32, 25, 20, 2, 3, 5, "#34173e");
line(15, 24, 23, 16, 24, 17, 0, hairLight);
line(33, 24, 23, 32, 24, 17, 0, hairLight);
// Solid bell-shaped dress.
for (let z = 0; z <= 17; z++) {
const rx = 11.5 - z * 0.34;
const ry = 9.4 - z * 0.28;
for (let x = Math.ceil(24 - rx); x <= Math.floor(24 + rx); x++) {
for (let y = Math.ceil(25 - ry); y <= Math.floor(25 + ry); y++) {
const d = ((x - 24) / rx) ** 2 + ((y - 25) / ry) ** 2;
if (d > 1) continue;
let c = y < 23 ? violet : violetDark;
if (y < 20 && rand() < 0.08) c = violetLight;
if (d > 0.76 && z <= 1) c = gold;
if (d > 0.83 && z === 2 && x % 5 === 0) c = goldLight;
set(x, y, z, c);
}
}
}
ellipsoid(24, 25, 19, 6, 5, 8, violet);
ellipsoid(24, 20, 20, 4, 1, 6, violetLight);
box(23, 18, 16, 25, 18, 25, "#8f4ba9");
line(24, 17, 5, 24, 18, 15, 0, gold);
for (let z = 5; z <= 15; z += 3) {
set(23, 17 + Math.floor(z / 7), z, goldLight);
set(25, 17 + Math.floor(z / 7), z, goldLight);
}
line(21, 19, 25, 24, 18, 22, 0, gold);
line(27, 19, 25, 24, 18, 22, 0, gold);
sphere(24, 18, 22, 1.4, "#80e6df");
// High, flared collar framing the face.
ellipsoid(24, 25, 27, 8, 6, 4, violetDark);
ellipsoid(24, 23, 29, 6, 5, 3, violet);
line(17, 23, 26, 18, 21, 32, 1, violetLight);
line(31, 23, 26, 30, 21, 32, 1, violetLight);
line(17, 21, 32, 19, 19, 33, 0, gold);
line(31, 21, 32, 29, 19, 33, 0, gold);
// Raised sleeves and open hands, cupping the spell.
line(19, 24, 24, 15, 19, 25, 3, violet);
sphere(15, 19, 25, 3, violetLight);
line(15, 19, 25, 18, 13, 25, 2, violet);
line(29, 24, 24, 33, 19, 25, 3, violet);
sphere(33, 19, 25, 3, violetLight);
line(33, 19, 25, 30, 13, 25, 2, violet);
sphere(18, 13, 25, 2.3, violetDark);
sphere(30, 13, 25, 2.3, violetDark);
sphere(19, 11, 25, 1.8, skin);
sphere(29, 11, 25, 1.8, skin);
line(19, 11, 25, 20, 10, 27, 0, "#ffd7bc");
line(29, 11, 25, 28, 10, 27, 0, "#ffd7bc");
line(19, 11, 24, 20, 10, 23, 0, skin);
line(29, 11, 24, 28, 10, 23, 0, skin);
line(17, 14, 25, 19, 13, 25, 0, gold);
line(31, 14, 25, 29, 13, 25, 0, gold);
// Big friendly face.
ellipsoid(24, 22, 32, 6.5, 5.5, 6.5, skin);
ellipsoid(24, 17, 29, 4, 1, 2, "#f5c7af");
set(24, 16, 30, "#d9918e");
set(23, 16, 28, "#a94772");
set(24, 16, 28, "#a94772");
set(25, 16, 28, "#a94772");
ellipsoid(19, 17, 30, 1.5, 1, 1, "#e99ca6");
ellipsoid(29, 17, 30, 1.5, 1, 1, "#e99ca6");
for (const x of [21, 27]) {
ellipsoid(x, 16, 33, 2, 1, 2, "#fff3e8");
ellipsoid(x, 15, 33, 1, 1, 1.5, "#42bcb8");
set(x, 14, 33, "#172c43");
set(x, 14, 34, "#ffffff");
line(x - 1, 15, 35, x + 1, 15, 35, 0, hair);
}
line(19, 16, 36, 22, 16, 36, 0, hair);
line(26, 16, 36, 29, 16, 36, 0, hair);
// Rounded crown, swooping bangs and long face-framing curls.
ellipsoid(24, 23, 39, 8, 6, 5, hair);
ellipsoid(20, 18, 37, 4, 2, 2, "#32173b");
ellipsoid(27, 18, 38, 4, 2, 2, hair);
line(19, 17, 37, 23, 16, 36, 1, hairLight);
line(29, 17, 38, 26, 16, 36, 1, hairLight);
ellipsoid(17, 20, 28, 2, 3, 8, hair);
ellipsoid(31, 20, 28, 2, 3, 8, hair);
line(16, 19, 32, 16, 19, 24, 0, hairLight);
line(32, 19, 32, 32, 19, 24, 0, hairLight);
line(20, 17, 41, 23, 17, 42, 0, hairLight);
sphere(24, 17, 39, 1, gold);
set(24, 16, 39, "#f6a9e1");
// The entire floating spell is one bobbing, color-cycling part.
part("magicBall", [24, 9, 25]);
sphere(24, 9, 25, 4.1, "#a92be5");
sphere(24, 7, 26, 2.6, "#ed42d9");
sphere(24, 5, 26, 1.2, "#fff0ff");
for (let i = 0; i <= 32; i++) {
const a = i * Math.PI / 10;
const r = 4.3 + 0.35 * Math.sin(i * 1.7);
const x = 24 + Math.cos(a) * r;
const y = 9 + Math.sin(a) * r;
const z = 24 + i * 0.085;
sphere(x, y, z, i % 5 === 0 ? 1 : 0.65,
i % 3 === 0 ? "#fff0ff" : i % 3 === 1 ? "#fa5bd2" : "#8333e9");
}
for (let i = 0; i < 14; i++) {
const a = rand() * Math.PI * 2;
const h = (rand() - 0.5) * 11;
const r = 5 + rand() * 1.5;
set(24 + Math.cos(a) * r, 9 + Math.sin(a) * r, 25 + h,
rand() < 0.4 ? "#ffffff" : "#e865ef");
}
animate("magicBall", { type: "bob", axis: "z", speed: 2, amplitude: 1.5 });
animate("magicBall", {
type: "colors",
palette: ["#ed32c7", "#862de2", "#ff8ddd", "#ffffff"],
pattern: "wave",
glow: 0.9
});
part("body", [24, 24, 0]);import { draw } from "./assets/voxel";
import { hechicera } from "./assets/hechicera";
// Every frame: standing on (x, y), the centre of its base.
draw(ctx, hechicera, 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 hechicera
# With Fogón's tools (connector)
add_assets({ slug: "<your-game>", ids: ["hechicera"] })
# It lands in client/assets/hechicera.ts
# https://fogon.page/object/hechicera