<!-- SOLID CITY · part 3630 -->
ly)
  [[-52, -40, -14], [52, 30, -14], [-55, 60, -30], [55, 120, -32]].forEach(function (p) {
    var h = 34 + R() * 6;
    if (R() < 0.5) pineTree(p[0], p[1], p[2], h); else ohiaTree(p[0], p[1], p[2], h);
  });

  // ---------- switchback road: climbs C → B → A ----------
  var roadMat = new T.MeshLambertMaterial({ color: 0x4a3f30 });
  function roadSeg(x1, z1, y1, x2, z2, y2, w) {
    w = w || 9;
    var len = Math.hypot(x2 - x1, z2 - z1);
    var seg = new T.Mesh(new T.BoxGeometry(len, 1.1, w), roadMat);
    seg.position.set((x1 + x2) / 2, (y1 + y2) / 2 - 0.2, (z1 + z2) / 2);
    seg.rotation.y = -Math.atan2(z2 - z1, x2 - x1);
    // pitch to follow the climb
    var pitch = Math.atan2(y2 - y1, len);
    seg.rotateOnAxis(new T.Vector3(0, 0, 1), 0); // keep flat-ish; terraces carry the height
    root.add(seg);
  }
  // road path: enters low from the south, switchbacks up
  var P1 = [0, 150, -36], P2 = [-44, 120, -36], P3 = [-44, 40, -27],
      P4 = [40, 40, -27], P5 = [40, -40, -9], P6 = [-36, -40, -9], P7 = [-36, -85, 0];
  var path = [P1, P2, P3, P4, P5, P6, P7];
  for (var sgi = 0; sgi < path.length - 1; sgi++) {
    var A0 = path[sgi], B0 = path[sgi + 1];
    roadSeg(A0[0], A0[1], A0[2], B0[0], B0[1], B0[2]);
  }
  // torches along the road
  var torches = [];
  path.forEach(function (p, idx) {
    if (idx % 2) return;
    [6.5, -6.5].forEach(function (off) {
      var pole = new T.Mesh(new T.CylinderGeometry(0.22, 0.3, 4.6, 6), woodDarkMat);
      pole.position.set(p[0] + off, p[2] + 2.3, p[1]); root.add(pole);
      var fl = new T.Mesh(new T.ConeGeometry(0.55, 1.7, 8),
        new T.MeshBasicMaterial({ color: C.fire, transparent: true, opacity: 0.92 }));
      fl.position.set(p[0] + off, p[2] + 5.3, p[1]); fl.name = 'flame'; root.add(fl);
      var pl = new T.PointLight(0xff9a40, 1.0, 34);
      pl.position.set(p[0] + off, p[2] + 5.6, p[1]); root.add(pl);
      torches.push({ fl: fl, pl: pl, seed: R() * 10 });
      foot.push([p[0] + off, p[1], 0.9, 0.9, p[2], p[2] + 4.6, 0]);
    });
  });

  // ---------- fireflies of warm light: village glow ----------
  var glow = new T.PointLight(0xffb050, 1.4, 220, 1.2);
  glow.position.set(0, 14, 0); root.add(glow);

  root.userData = {
    footprint: foot, center: { x: 0, z: 0 }, radius: 320, height: 60,
    terraceTops: TER.map(function (t) { return { x: t.x, z: t.z, r: t.r, topY: t.y + 1.1 }; }),
    update: function (t) {
      var hale = haleRef.g;
      if (hale) {
        hale.userData.flame.scale.y = 1 + Math.sin(t * 5.2) * 0.16;
        hale.userData.fireLight.intensity = 2.1 + Math.sin(t * 5.2) * 0.5 + Math.sin(t * 13.7) * 0.2;
      }
      for (var k = 0; k < torches.length; k++) {
        var tc = torches[k];
        tc.fl.scale.y = 1 + Math.sin(t * 6 + tc.seed) * 0.18;
        tc.pl.intensity = 0.95 + Math.sin(t * 6 + tc.seed) * 0.22;
      }
      glow.intensity = 1.35 + Math.sin(t * 1.7) * 0.12;
    }
  };
  return root;
}
export default createMaunaVillage;


===== FILE: public/city/village-mauna.js.bak-grow20261011 =====
/* SOLID CITY — KAUHALE MAUNA, THE MOUNTAIN VILLAGE (2026-10-11, by order of the King)
 * "Drive me to a road up in the mountains where we can make a mountain village with trees."
 * A mountainside village on three terraces: gathering hale and fire above,
 * hale-huts mid and low, a lookout toward the city lights, and a forest of
 * GIANT trees — the King's wish: towering 25-40 m ancients, thick trunks,
 * broad canopies. The village nestles among them.
 * Self-contained ES module. Local frame: terrace tops at y=0 (A), -18 (B), -36 (C).
 *
 *   import { createMaunaVillage } from '/city/village-mauna.js';
 *   const g = createMaunaVillage({ THREE, position: {x, y, z} });
 *   // g.userData: footprint, update(t), terraceTops
 */
function mulberry(a) { return function () { a |= 0; a = a + 0x6D2B79F5 | 0; var t = Math.imul(a ^ a >>> 15, 1 | a); t = t + Math.imul(t ^ t >>> 7, 61 | t) ^ t; return ((t ^ t >>> 14) >>> 0) / 4294967296; }; }
export function createMaunaVillage(o) {
  var T = o.THREE, P = o.position || { x: 0, y: 0, z: 0 };
  var root = new T.Group(); root.name = 'village-mauna'; root.position.set(P.x, P.y, P.z);
  var foot = [];
  var haleRef = { g: null };
  var R = mulberry(20261011);
  var C = {
    basalt: 0x1c1a20, wood: 0x5a4028, woodDark: 0x3a2a18, thatch: 0x8a6a3a,
    leaf: 0x1e4a24, leafDeep: 0x14331a, trunk: 0x4a3420,
    fire: 0xff9a30, warm: 0xffc060, gold: 0xd8aa48
  };
  var basaltMat = new T.MeshLambertMaterial({ color: C.basalt });
  var woodMat = new T.MeshLambertMaterial({ color: C.wood });
  var woodDarkMat = new T.MeshLambertMaterial({ color: C.woodDark });
  var thatchMat = new T.MeshLambertMaterial({ color: C.thatch });
  var leafMat = new T.MeshLambertMaterial({ color: C.leaf });
  var leafDeepMat = new T.MeshLambertMaterial({ color: C.leafDeep });
  var trunkMat = new T.MeshLambertMaterial({ color: C.trunk });
  var terraceMat = new T.MeshLambertMaterial({ colo