608 tris0,51 × 0,95 × 0,44 m
Use no código
Fazer remix no editornightstand.js · 181 linhas
Módulo ES autocontido — depende apenas do three. Chame a factory e adicione o grupo à sua cena.
/**
* Nightstand — Codels 3D model library
* License: CC0-1.0 · Units: meters · Y-up · Front: +Z · Origin: center of the base (y = 0)
* Triangles: 608 · Size (W × H × D): 0.51 × 0.95 × 0.44 m
*
* Usage:
* import { createNightstand } from './nightstand.js';
*
* const model = createNightstand();
* model.position.set(0, 0, 0);
* scene.add(model);
*/
import * as THREE from 'three';
const deg = THREE.MathUtils.degToRad;
// Revolve a 2D profile [[radius, y], ...] around the Y axis.
function lathe(points, segments, phiStart = 0, phiLength = Math.PI * 2) {
return new THREE.LatheGeometry(points.map(([x, y]) => new THREE.Vector2(x, y)), segments, phiStart, phiLength);
}
// Extrude a 2D outline along Z (centered). bevel = [thickness, size, segments].
function extrude(outline, depth, holes = [], bevel = null) {
const shape = new THREE.Shape(outline.map(([x, y]) => new THREE.Vector2(x, y)));
for (const hole of holes) shape.holes.push(new THREE.Path(hole.map(([x, y]) => new THREE.Vector2(x, y))));
const options = bevel
? { depth, bevelEnabled: true, bevelThickness: bevel[0], bevelSize: bevel[1], bevelSegments: bevel[2] }
: { depth, bevelEnabled: false };
return new THREE.ExtrudeGeometry(shape, options).translate(0, 0, -depth / 2);
}
export function createNightstand() {
const root = new THREE.Group();
root.name = 'Nightstand';
// Materials
const woodMat = new THREE.MeshStandardMaterial({ name: 'wood', color: 0x9a6338, roughness: 0.8, flatShading: true });
const panelMat = new THREE.MeshStandardMaterial({ name: 'panel', color: 0xa67650, roughness: 0.75, flatShading: true });
const darkMat = new THREE.MeshStandardMaterial({ name: 'dark', color: 0x593920, roughness: 0.95, flatShading: true });
const brassMat = new THREE.MeshStandardMaterial({ name: 'brass', color: 0xd4a84e, roughness: 0.35, metalness: 0.5, flatShading: true });
const ceramicMat = new THREE.MeshStandardMaterial({ name: 'ceramic', color: 0x5f86a3, roughness: 0.35, flatShading: true });
const shadeMat = new THREE.MeshStandardMaterial({ name: 'shade', color: 0xefdcb4, roughness: 1, emissive: 0xd7c6a2, emissiveIntensity: 0.45, flatShading: true, side: THREE.DoubleSide });
const bulbMat = new THREE.MeshStandardMaterial({ name: 'bulb', color: 0xfff4d6, roughness: 0.8, emissive: 0xffd27a, emissiveIntensity: 1.2, flatShading: true });
const redMat = new THREE.MeshStandardMaterial({ name: 'red', color: 0xa3413a, roughness: 0.85, flatShading: true });
const greenMat = new THREE.MeshStandardMaterial({ name: 'green', color: 0x4b6b4a, roughness: 0.85, flatShading: true });
const paperMat = new THREE.MeshStandardMaterial({ name: 'paper', color: 0xefe7d2, roughness: 1, flatShading: true });
// Shared geometries
const cylinderGeo = new THREE.CylinderGeometry(0.024, 0.0156, 0.11, 4);
const boxGeo = new THREE.BoxGeometry(0.02, 0.454, 0.4);
// Parts
const leg = new THREE.Mesh(cylinderGeo, woodMat);
leg.name = 'leg';
leg.position.set(-0.21, 0.055, -0.17);
leg.rotation.set(0, deg(45), 0);
root.add(leg);
const leg2 = new THREE.Mesh(cylinderGeo, woodMat);
leg2.name = 'leg';
leg2.position.set(-0.21, 0.055, 0.17);
leg2.rotation.set(0, deg(45), 0);
root.add(leg2);
const leg3 = new THREE.Mesh(cylinderGeo, woodMat);
leg3.name = 'leg';
leg3.position.set(0.21, 0.055, -0.17);
leg3.rotation.set(0, deg(45), 0);
root.add(leg3);
const leg4 = new THREE.Mesh(cylinderGeo, woodMat);
leg4.name = 'leg';
leg4.position.set(0.21, 0.055, 0.17);
leg4.rotation.set(0, deg(45), 0);
root.add(leg4);
const side = new THREE.Mesh(boxGeo, woodMat);
side.name = 'side';
side.position.set(-0.23, 0.327, 0);
root.add(side);
const side2 = new THREE.Mesh(boxGeo, woodMat);
side2.name = 'side';
side2.position.set(0.23, 0.327, 0);
root.add(side2);
const bottom = new THREE.Mesh(new THREE.BoxGeometry(0.44, 0.02, 0.4), woodMat);
bottom.name = 'bottom';
bottom.position.set(0, 0.11, 0);
root.add(bottom);
const backPanel = new THREE.Mesh(new THREE.BoxGeometry(0.44, 0.454, 0.012), darkMat);
backPanel.name = 'backPanel';
backPanel.position.set(0, 0.327, -0.194);
root.add(backPanel);
const skirt = new THREE.Mesh(new THREE.BoxGeometry(0.47, 0.03, 0.02), woodMat);
skirt.name = 'skirt';
skirt.position.set(0, 0.103, 0.188);
root.add(skirt);
const top = new THREE.Mesh(extrude([[0.247, 0.1919], [0.2369, 0.202], [-0.2369, 0.202], [-0.247, 0.1919], [-0.247, -0.1919], [-0.2369, -0.202], [0.2369, -0.202], [0.247, -0.1919]], 0.01, [], [0.008, 0.008, 1]), woodMat);
top.name = 'top';
top.position.set(0, 0.567, 0.005);
top.rotation.set(deg(-90), 0, 0);
root.add(top);
const drawer = new THREE.Mesh(extrude([[0.219, 0.0451], [0.211, 0.053], [-0.211, 0.053], [-0.219, 0.0451], [-0.219, -0.0451], [-0.211, -0.053], [0.211, -0.053], [0.219, -0.0451]], 0.008, [], [0.006, 0.006, 1]), panelMat);
drawer.name = 'drawer';
drawer.position.set(0, 0.485, 0.196);
root.add(drawer);
const knob = new THREE.Group();
knob.name = 'knob';
knob.position.set(0, 0.485, 0.206);
root.add(knob);
const knobStem = new THREE.Mesh(new THREE.CylinderGeometry(0.0063, 0.0084, 0.0126, 6), brassMat);
knobStem.name = 'knobStem';
knobStem.position.set(0, 0, 0.0063);
knobStem.rotation.set(deg(90), 0, 0);
knob.add(knobStem);
const knobHead = new THREE.Mesh(new THREE.SphereGeometry(0.014, 6, 4), brassMat);
knobHead.name = 'knobHead';
knobHead.position.set(0, 0, 0.0175);
knobHead.scale.set(1, 1, 0.7);
knob.add(knobHead);
const drawerShelf = new THREE.Mesh(new THREE.BoxGeometry(0.44, 0.016, 0.38), woodMat);
drawerShelf.name = 'drawerShelf';
drawerShelf.position.set(0, 0.42, 0);
root.add(drawerShelf);
const book = new THREE.Mesh(new THREE.BoxGeometry(0.03, 0.16, 0.13), redMat);
book.name = 'book';
book.position.set(-0.165, 0.2, 0.02);
root.add(book);
const book2 = new THREE.Mesh(new THREE.BoxGeometry(0.025, 0.15, 0.13), greenMat);
book2.name = 'book';
book2.position.set(-0.1335, 0.195, 0.02);
root.add(book2);
const book3 = new THREE.Mesh(new THREE.BoxGeometry(0.035, 0.17, 0.13), paperMat);
book3.name = 'book';
book3.position.set(-0.0995, 0.205, 0.02);
root.add(book3);
const book4 = new THREE.Mesh(new THREE.BoxGeometry(0.025, 0.15, 0.12), redMat);
book4.name = 'book';
book4.position.set(-0.043, 0.195, 0.02);
book4.rotation.set(0, 0, deg(-22));
root.add(book4);
const lampBase = new THREE.Mesh(lathe([[0.001, 0], [0.045, 0], [0.052, 0.012], [0.064, 0.05], [0.06, 0.1], [0.044, 0.14], [0.018, 0.165], [0.012, 0.18], [0.001, 0.18]], 8), ceramicMat);
lampBase.name = 'lampBase';
lampBase.position.set(-0.08, 0.58, -0.05);
root.add(lampBase);
const lampStem = new THREE.Mesh(new THREE.CylinderGeometry(0.007, 0.007, 0.09, 5), brassMat);
lampStem.name = 'lampStem';
lampStem.position.set(-0.08, 0.805, -0.05);
root.add(lampStem);
const bulb = new THREE.Mesh(new THREE.SphereGeometry(0.03, 6, 4), bulbMat);
bulb.name = 'bulb';
bulb.position.set(-0.08, 0.85, -0.05);
root.add(bulb);
const lampShade = new THREE.Mesh(new THREE.CylinderGeometry(0.075, 0.115, 0.15, 10, 1, true), shadeMat);
lampShade.name = 'lampShade';
lampShade.position.set(-0.08, 0.865, -0.05);
root.add(lampShade);
const finial = new THREE.Mesh(new THREE.SphereGeometry(0.008, 4, 3), brassMat);
finial.name = 'finial';
finial.position.set(-0.08, 0.945, -0.05);
root.add(finial);
const bedsideBook = new THREE.Group();
bedsideBook.name = 'bedsideBook';
bedsideBook.position.set(0.11, 0.58, 0.06);
bedsideBook.rotation.set(0, deg(-18), 0);
root.add(bedsideBook);
const cover = new THREE.Mesh(new THREE.BoxGeometry(0.15, 0.03, 0.21), greenMat);
cover.name = 'cover';
cover.position.set(0, 0.015, 0);
bedsideBook.add(cover);
const pages = new THREE.Mesh(new THREE.BoxGeometry(0.14, 0.022, 0.01), paperMat);
pages.name = 'pages';
pages.position.set(0, 0.015, 0.1);
bedsideBook.add(pages);
root.traverse((o) => {
if (o.isMesh) {
o.castShadow = true;
o.receiveShadow = true;
}
});
return root;
}
export default createNightstand;
Avaliações e comentários
0 comentário
Nenhum comentário ainda. Conte como você usou este modelo ou o que poderia melhorar.
Modelos relacionados
Mesma categoria ou tags parecidas









