← City3D assetfogon/ph-de-barrio
PH de barrio
Drag to turn it// «PH de barrio» · gpt-6-sol (medium)
// A two-story Buenos Aires PH house: a narrow brick facade with a garage door and a front door on the ground floor, a small balcony with an iron railing and a potted plant on the upper floor, a little terrace on the roof with a clothesline and a white water tank. Warm red brick with white window frames.
// Buenos Aires PH: brick facade, garage, balcony and roof terrace.
const brick = ["#b9513f", "#c45b45", "#a94739"];
const mortar = "#ddaa8d";
const cream = "#f3eee0";
const concrete = "#d6d0c2";
const iron = "#244d42";
const opening = (x, z) =>
(x >= 10 && x <= 28 && z >= 2 && z <= 15) || // garage
(x >= 31 && x <= 37 && z >= 2 && z <= 15) || // front door
(x >= 14 && x <= 27 && z >= 22 && z <= 33) || // balcony doors
(x >= 30 && x <= 37 && z >= 24 && z <= 32); // upper window
// Pavement, doorstep and the house's solid floor.
box(5, 5, 0, 42, 39, 0, "#bab9b0");
box(5, 5, 0, 42, 7, 0, "#929693");
for (let x = 7; x <= 40; x += 8) box(x, 6, 0, x, 7, 0, "#a5a9a5");
box(7, 10, 0, 40, 38, 1, concrete);
box(6, 8, 0, 41, 10, 1, "#d4d0c6");
// Brick side and back walls, with a little variation.
for (let z = 2; z <= 34; z++) {
for (let y = 11; y <= 38; y++) {
const c = z % 3 === 0 ? mortar : brick[Math.floor(rand() * brick.length)];
box(7, y, z, 8, y, z, c);
box(39, y, z, 40, y, z, c);
}
for (let x = 9; x <= 38; x++) {
box(x, 37, z, x, 38, z,
z % 3 === 0 ? mortar : brick[Math.floor(rand() * brick.length)]);
}
}
// Front brickwork: recessed openings remain legible from the street.
for (let z = 2; z <= 34; z++) {
for (let x = 7; x <= 40; x++) {
if (opening(x, z)) continue;
const joint = z % 3 === 0 || (x + (Math.floor(z / 3) % 2) * 3) % 7 === 0;
const c = joint ? mortar : brick[Math.floor(rand() * brick.length)];
box(x, 10, z, x, 12, z, c);
set(x, 9, z, c);
}
}
// Strong pale bands separate the two stories.
box(7, 9, 17, 40, 12, 18, "#e7d8c6");
box(7, 8, 17, 40, 8, 17, "#c6b6a5");
box(7, 10, 18, 40, 38, 19, concrete);
box(6, 9, 35, 41, 39, 36, "#e4ded0");
box(6, 8, 35, 41, 9, 35, "#bbb4a8");
// Wide corrugated garage shutter.
box(10, 9, 2, 28, 9, 15, "#e9e7df");
box(11, 8, 3, 27, 8, 14, "#818b8a");
for (let z = 3; z <= 14; z++) {
box(11, 7, z, 27, 7, z,
z % 3 === 0 ? "#64726f" : z % 3 === 1 ? "#a2aaa5" : "#899491");
}
box(9, 7, 2, 10, 9, 16, cream);
box(28, 7, 2, 29, 9, 16, cream);
box(10, 7, 15, 28, 9, 16, cream);
box(18, 6, 5, 21, 6, 5, "#344943");
box(19, 6, 4, 20, 6, 4, "#d8cdb5");
// Green front door with a glazed transom and bright white surround.
box(30, 8, 2, 30, 10, 16, cream);
box(38, 8, 2, 38, 10, 16, cream);
box(30, 8, 16, 38, 10, 16, cream);
box(31, 8, 2, 37, 8, 10, "#276052");
box(32, 7, 3, 36, 7, 9, "#347565");
box(31, 7, 11, 37, 7, 15, "#b8d5cd");
box(34, 6, 11, 34, 6, 15, cream);
box(32, 6, 13, 36, 6, 13, cream);
set(36, 6, 7, "#e7c167");
box(31, 6, 1, 37, 8, 1, "#eee7d8");
// Small colorful PH tile above the doorway.
box(32, 7, 17, 37, 7, 18, "#248579");
box(33, 6, 17, 36, 6, 17, "#f0c869");
set(33, 5, 17, cream);
set(35, 5, 17, cream);
set(36, 5, 17, cream);
// Upstairs French doors: dark glazing framed in white.
box(14, 9, 22, 27, 9, 33, "#d9f0e9");
box(15, 8, 23, 26, 8, 32, "#437d83");
box(16, 7, 24, 19, 7, 31, "#86b4b0");
box(22, 7, 24, 25, 7, 31, "#86b4b0");
box(14, 7, 22, 15, 9, 33, cream);
box(26, 7, 22, 27, 9, 33, cream);
box(14, 7, 33, 27, 9, 33, cream);
box(20, 7, 22, 21, 8, 32, cream);
box(15, 7, 28, 26, 7, 28, cream);
set(19, 6, 25, "#e4bd61");
set(22, 6, 25, "#e4bd61");
// A smaller upstairs window.
box(30, 9, 24, 37, 9, 32, "#eff2e8");
box(31, 8, 25, 36, 8, 31, "#477f85");
box(32, 7, 26, 35, 7, 30, "#9bc1b8");
box(30, 7, 24, 30, 9, 32, cream);
box(37, 7, 24, 37, 9, 32, cream);
box(30, 7, 32, 37, 9, 32, cream);
box(33, 7, 25, 34, 7, 31, cream);
box(30, 6, 23, 38, 9, 23, "#ebe3d4");
// Projecting balcony and its chunky dark-green iron railing.
box(11, 6, 19, 35, 12, 20, "#dfd8ca");
box(11, 5, 19, 35, 5, 19, "#b5aea1");
box(11, 5, 21, 35, 5, 21, iron);
box(11, 5, 26, 35, 5, 26, iron);
for (let x = 11; x <= 35; x += 3) {
box(x, 5, 21, x, 5, 26, iron);
set(x, 5, 27, "#d4b762");
}
for (const x of [11, 35]) {
box(x, 6, 21, x, 11, 21, iron);
box(x, 6, 26, x, 11, 26, iron);
for (let y = 7; y <= 10; y += 3) box(x, y, 21, x, y, 26, iron);
}
// Terracotta pot and leafy balcony plant.
box(30, 8, 21, 33, 10, 23, "#b76843");
box(29, 8, 23, 34, 10, 23, "#d68454");
box(30, 8, 24, 33, 10, 24, "#554638");
line(31, 9, 24, 31, 9, 29, 0, "#52763e");
for (const [x, y, z] of [
[30, 9, 26], [32, 9, 27], [29, 9, 27], [33, 9, 28],
[31, 8, 29], [30, 10, 28], [32, 10, 26]
]) sphere(x, y, z, 1, rand() > 0.5 ? "#499651" : "#72ac55");
set(30, 8, 29, "#eebc75");
set(33, 9, 28, "#f2b4a2");
// Roof terrace: low brick parapet, pale coping and a little door hatch.
box(7, 10, 37, 40, 11, 39, "#b95743");
box(7, 10, 40, 40, 11, 40, "#eee7d9");
box(7, 12, 37, 8, 38, 39, "#b95743");
box(39, 12, 37, 40, 38, 39, "#b95743");
box(7, 37, 37, 40, 38, 39, "#b95743");
box(7, 12, 40, 8, 38, 40, "#eee7d9");
box(39, 12, 40, 40, 38, 40, "#eee7d9");
box(7, 37, 40, 40, 38, 40, "#eee7d9");
box(10, 13, 37, 17, 19, 40, "#d1c9ba");
box(11, 12, 38, 16, 12, 40, "#41665c");
// Clothesline above the front of the terrace.
box(12, 16, 37, 13, 17, 43, iron);
box(27, 16, 37, 28, 17, 43, iron);
line(13, 16, 43, 27, 16, 43, 0, "#e8e0cb");
box(15, 16, 40, 18, 16, 42, "#f1e6d3");
box(20, 16, 39, 23, 16, 42, "#e8867a");
box(25, 16, 40, 26, 16, 42, "#7ab1c7");
for (const x of [15, 18, 20, 23, 25, 26]) set(x, 15, 43, "#d7b563");
// White rooftop water tank on a short stand.
for (const x of [29, 35]) for (const y of [28, 34])
box(x, y, 37, x, y, 39, "#92958d");
box(29, 28, 39, 35, 34, 39, "#adb1a8");
cylinder(32, 31, 40, 4, 5, "#f0f0e8");
cylinder(32, 31, 44, 4, 1, "#ffffff");
box(29, 27, 41, 35, 27, 41, "#d4ddd7");
box(29, 27, 43, 35, 27, 43, "#d4ddd7");
box(31, 29, 45, 33, 32, 45, "#d9ded9");import { draw } from "./assets/voxel";
import { phDeBarrio } from "./assets/ph-de-barrio";
// Every frame: standing on (x, y), the centre of its base.
draw(ctx, phDeBarrio, 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 ph-de-barrio
# With Fogón's tools (connector)
add_assets({ slug: "<your-game>", ids: ["ph-de-barrio"] })
# It lands in client/assets/ph-de-barrio.ts
# https://fogon.page/object/ph-de-barrio