Codels
1,8 mil tris7,28 × 8,42 × 4,25 m
Módulo ES autocontido — depende apenas do three. Chame a factory e adicione o grupo à sua cena.
/**
 * Space Probe — Codels 3D model library
 * License: CC0-1.0 · Units: meters · Y-up · Front: +Z · Origin: center of the model (it floats — pickups, planets)
 * Triangles: 1,832 · Size (W × H × D): 7.28 × 8.42 × 4.25 m
 *
 * Usage:
 *   import { createSpaceProbe } from './space-probe.js';
 *   
 *   const model = createSpaceProbe();
 *   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);
}

export function createSpaceProbe() {
  const root = new THREE.Group();
  root.name = 'SpaceProbe';

  // Materials
  const dishMat = new THREE.MeshStandardMaterial({ name: 'dish', color: 0xeef0f3, roughness: 0.45, metalness: 0.15, flatShading: true });
  const foilMat = new THREE.MeshStandardMaterial({ name: 'foil', color: 0xd9a83c, roughness: 0.35, metalness: 0.7, flatShading: true });
  const metalMat = new THREE.MeshStandardMaterial({ name: 'metal', color: 0xb4bcc6, roughness: 0.35, metalness: 0.7, flatShading: true });
  const darkMat = new THREE.MeshStandardMaterial({ name: 'dark', color: 0x2f343c, roughness: 0.55, metalness: 0.45, flatShading: true });
  const rtgMat = new THREE.MeshStandardMaterial({ name: 'rtg', color: 0x4a3a34, roughness: 0.5, metalness: 0.4, emissive: 0xff6a2a, emissiveIntensity: 0.6, flatShading: true });
  const glowMat = new THREE.MeshStandardMaterial({ name: 'glow', color: 0x4fd8ff, roughness: 0.4, emissive: 0x38c8ff, emissiveIntensity: 1.2, flatShading: true });
  const lensMat = new THREE.MeshStandardMaterial({ name: 'lens', color: 0x1d2a36, roughness: 0.1, metalness: 0.6, flatShading: true });

  // Shared geometries
  const coneGeo = new THREE.ConeGeometry(0.07, 0.14, 6);
  const cylinderGeo = new THREE.CylinderGeometry(0.018, 0.022, 1.4955, 4);
  const cylinderGeo2 = new THREE.CylinderGeometry(0.17, 0.17, 0.44, 8);
  const boxGeo = new THREE.BoxGeometry(0.6, 0.38, 0.03);
  const cylinderGeo3 = new THREE.CylinderGeometry(0.2, 0.2, 0.05, 8);
  const cylinderGeo4 = new THREE.CylinderGeometry(0.07, 0.07, 0.04, 6);
  const cylinderGeo5 = new THREE.CylinderGeometry(0.012, 0.02, 3.9272, 4);

  // Parts
  const probe = new THREE.Group();
  probe.name = 'probe';
  probe.rotation.set(deg(-16), deg(-6), 0);
  root.add(probe);
  const bus = new THREE.Mesh(new THREE.CylinderGeometry(0.8, 0.8, 0.46, 10), metalMat);
  bus.name = 'bus';
  bus.position.set(0, 0, -0.42);
  bus.rotation.set(deg(90), 0, 0);
  probe.add(bus);
  const rearBlanket = new THREE.Mesh(new THREE.CylinderGeometry(0.72, 0.72, 0.06, 10), foilMat);
  rearBlanket.name = 'rearBlanket';
  rearBlanket.position.set(0, 0, -0.68);
  rearBlanket.rotation.set(deg(90), 0, 0);
  probe.add(rearBlanket);
  const foilBand = new THREE.Mesh(new THREE.CylinderGeometry(0.82, 0.82, 0.12, 10), foilMat);
  foilBand.name = 'foilBand';
  foilBand.position.set(0, 0, -0.42);
  foilBand.rotation.set(deg(90), 0, 0);
  probe.add(foilBand);
  const dishMount = new THREE.Mesh(new THREE.CylinderGeometry(0.32, 0.4, 0.4, 8), darkMat);
  dishMount.name = 'dishMount';
  dishMount.position.set(0, 0, -0.07);
  dishMount.rotation.set(deg(90), 0, 0);
  probe.add(dishMount);
  const goldenRecord = new THREE.Mesh(new THREE.CylinderGeometry(0.17, 0.17, 0.03, 10), foilMat);
  goldenRecord.name = 'goldenRecord';
  goldenRecord.position.set(0.7379, 0.2397, -0.42);
  goldenRecord.rotation.set(0, 0, deg(-72));
  probe.add(goldenRecord);
  const cylinder7 = new THREE.Mesh(new THREE.CylinderGeometry(0.06, 0.06, 0.012, 8), darkMat);
  cylinder7.position.set(0.7569, 0.2459, -0.42);
  cylinder7.rotation.set(0, 0, deg(-72));
  probe.add(cylinder7);
  const thruster1 = new THREE.Mesh(coneGeo, darkMat);
  thruster1.name = 'thruster1';
  thruster1.position.set(0.3889, 0.3889, -0.76);
  thruster1.rotation.set(deg(-90), 0, 0);
  probe.add(thruster1);
  const thruster2 = new THREE.Mesh(coneGeo, darkMat);
  thruster2.name = 'thruster2';
  thruster2.position.set(0.3889, -0.3889, -0.76);
  thruster2.rotation.set(deg(-90), 0, 0);
  probe.add(thruster2);
  const thruster3 = new THREE.Mesh(coneGeo, darkMat);
  thruster3.name = 'thruster3';
  thruster3.position.set(-0.3889, -0.3889, -0.76);
  thruster3.rotation.set(deg(-90), 0, 0);
  probe.add(thruster3);
  const thruster4 = new THREE.Mesh(coneGeo, darkMat);
  thruster4.name = 'thruster4';
  thruster4.position.set(-0.3889, 0.3889, -0.76);
  thruster4.rotation.set(deg(-90), 0, 0);
  probe.add(thruster4);
  const statusLight = new THREE.Mesh(new THREE.BoxGeometry(0.14, 0.08, 0.03), glowMat);
  statusLight.name = 'statusLight';
  statusLight.position.set(0.25, 0.4, -0.72);
  probe.add(statusLight);
  const highGainAntenna = new THREE.Group();
  highGainAntenna.name = 'highGainAntenna';
  highGainAntenna.position.set(0, 0, 0.06);
  highGainAntenna.rotation.set(deg(90), 0, 0);
  probe.add(highGainAntenna);
  const dish = new THREE.Mesh(lathe([[0.001, -0.07], [0.3, -0.0533], [0.6, -0.0033], [0.9, 0.08], [1.2, 0.1967], [1.5, 0.3467], [1.8, 0.53], [1.84, 0.572], [1.8, 0.6], [1.5, 0.4167], [1.2, 0.2667], [0.9, 0.15], [0.6, 0.0667], [0.3, 0.0167], [0.001, 0]], 18), dishMat);
  dish.name = 'dish';
  highGainAntenna.add(dish);
  const dishRim = new THREE.Mesh(new THREE.TorusGeometry(1.85, 0.045, 3, 18), darkMat);
  dishRim.name = 'dishRim';
  dishRim.position.set(0, 0.57, 0);
  dishRim.rotation.set(deg(90), 0, 0);
  highGainAntenna.add(dishRim);
  const panelRing = new THREE.Mesh(new THREE.TorusGeometry(0.99, 0.018, 3, 16), metalMat);
  panelRing.name = 'panelRing';
  panelRing.position.set(0, 0.1915, 0);
  panelRing.rotation.set(deg(90), 0, 0);
  highGainAntenna.add(panelRing);
  const cylinder17 = new THREE.Mesh(cylinderGeo, metalMat);
  cylinder17.position.set(0, 0.7355, 0.78);
  cylinder17.rotation.set(deg(-61.9613), 0, 0);
  highGainAntenna.add(cylinder17);
  const cylinder18 = new THREE.Mesh(cylinderGeo, metalMat);
  cylinder18.position.set(-0.6755, 0.7355, -0.39);
  cylinder18.rotation.set(deg(26.9629), deg(-13.2657), deg(-51.7518));
  highGainAntenna.add(cylinder18);
  const cylinder19 = new THREE.Mesh(cylinderGeo, metalMat);
  cylinder19.position.set(0.6755, 0.7355, -0.39);
  cylinder19.rotation.set(deg(26.9629), deg(13.2657), deg(51.7518));
  highGainAntenna.add(cylinder19);
  const subreflector = new THREE.Mesh(new THREE.CylinderGeometry(0.3, 0.18, 0.1, 10), metalMat);
  subreflector.name = 'subreflector';
  subreflector.position.set(0, 1.147, 0);
  highGainAntenna.add(subreflector);
  const lowGainAntenna = new THREE.Mesh(new THREE.ConeGeometry(0.12, 0.3, 8), dishMat);
  lowGainAntenna.name = 'lowGainAntenna';
  lowGainAntenna.position.set(0, 1.347, 0);
  highGainAntenna.add(lowGainAntenna);
  const feedHorn = new THREE.Mesh(new THREE.CylinderGeometry(0.14, 0.22, 0.3, 8), darkMat);
  feedHorn.name = 'feedHorn';
  feedHorn.position.set(0, 0.12, 0);
  highGainAntenna.add(feedHorn);
  const rtgBoom = new THREE.Mesh(new THREE.CylinderGeometry(0.05, 0.06, 3.1721, 5), metalMat);
  rtgBoom.name = 'rtgBoom';
  rtgBoom.position.set(-2.33, -0.375, -0.42);
  rtgBoom.rotation.set(0, 0, deg(98.1556));
  probe.add(rtgBoom);
  const cylinder24 = new THREE.Mesh(new THREE.CylinderGeometry(0.025, 0.025, 0.8597, 4), metalMat);
  cylinder24.position.set(-1.319, -0.41, -0.57);
  cylinder24.rotation.set(deg(-22.8452), deg(25.9984), deg(-97.6144));
  probe.add(cylinder24);
  const cylinder25 = new THREE.Mesh(new THREE.CylinderGeometry(0.025, 0.025, 1.1853, 4), metalMat);
  cylinder25.position.set(-1.9274, -0.5225, -0.57);
  cylinder25.rotation.set(deg(-15.4005), deg(17.6281), deg(-97.8237));
  probe.add(cylinder25);
  const rtg1 = new THREE.Group();
  rtg1.name = 'rtg1';
  rtg1.position.set(-2.3928, -0.404, -0.42);
  rtg1.rotation.set(0, 0, deg(98.1556));
  probe.add(rtg1);
  const rtgCore = new THREE.Mesh(cylinderGeo2, rtgMat);
  rtgCore.name = 'rtgCore';
  rtg1.add(rtgCore);
  const fin1 = new THREE.Mesh(boxGeo, darkMat);
  fin1.name = 'fin1';
  rtg1.add(fin1);
  const fin2 = new THREE.Mesh(boxGeo, darkMat);
  fin2.name = 'fin2';
  fin2.rotation.set(0, deg(60), 0);
  rtg1.add(fin2);
  const fin3 = new THREE.Mesh(boxGeo, darkMat);
  fin3.name = 'fin3';
  fin3.rotation.set(0, deg(120), 0);
  rtg1.add(fin3);
  const cylinder31 = new THREE.Mesh(cylinderGeo3, darkMat);
  cylinder31.position.set(0, 0.24, 0);
  rtg1.add(cylinder31);
  const rtg2 = new THREE.Group();
  rtg2.name = 'rtg2';
  rtg2.position.set(-2.9266, -0.4805, -0.42);
  rtg2.rotation.set(0, 0, deg(98.1556));
  probe.add(rtg2);
  const rtgCore2 = new THREE.Mesh(cylinderGeo2, rtgMat);
  rtgCore2.name = 'rtgCore';
  rtg2.add(rtgCore2);
  const fin12 = new THREE.Mesh(boxGeo, darkMat);
  fin12.name = 'fin1';
  rtg2.add(fin12);
  const fin22 = new THREE.Mesh(boxGeo, darkMat);
  fin22.name = 'fin2';
  fin22.rotation.set(0, deg(60), 0);
  rtg2.add(fin22);
  const fin32 = new THREE.Mesh(boxGeo, darkMat);
  fin32.name = 'fin3';
  fin32.rotation.set(0, deg(120), 0);
  rtg2.add(fin32);
  const cylinder37 = new THREE.Mesh(cylinderGeo3, darkMat);
  cylinder37.position.set(0, 0.24, 0);
  rtg2.add(cylinder37);
  const rtg3 = new THREE.Group();
  rtg3.name = 'rtg3';
  rtg3.position.set(-3.4604, -0.557, -0.42);
  rtg3.rotation.set(0, 0, deg(98.1556));
  probe.add(rtg3);
  const rtgCore3 = new THREE.Mesh(cylinderGeo2, rtgMat);
  rtgCore3.name = 'rtgCore';
  rtg3.add(rtgCore3);
  const fin13 = new THREE.Mesh(boxGeo, darkMat);
  fin13.name = 'fin1';
  rtg3.add(fin13);
  const fin23 = new THREE.Mesh(boxGeo, darkMat);
  fin23.name = 'fin2';
  fin23.rotation.set(0, deg(60), 0);
  rtg3.add(fin23);
  const fin33 = new THREE.Mesh(boxGeo, darkMat);
  fin33.name = 'fin3';
  fin33.rotation.set(0, deg(120), 0);
  rtg3.add(fin33);
  const cylinder43 = new THREE.Mesh(cylinderGeo3, darkMat);
  cylinder43.position.set(0, 0.24, 0);
  rtg3.add(cylinder43);
  const scienceBoom = new THREE.Mesh(new THREE.CylinderGeometry(0.05, 0.06, 2.1609, 5), metalMat);
  scienceBoom.name = 'scienceBoom';
  scienceBoom.position.set(1.83, 0.3, -0.42);
  scienceBoom.rotation.set(0, 0, deg(-82.0199));
  probe.add(scienceBoom);
  const cosmicRayBox = new THREE.Mesh(new THREE.BoxGeometry(0.5, 0.18, 0.18), foilMat);
  cosmicRayBox.name = 'cosmicRayBox';
  cosmicRayBox.position.set(1.7, 0.36, -0.42);
  cosmicRayBox.rotation.set(0, 0, deg(8));
  probe.add(cosmicRayBox);
  const scanPlatform = new THREE.Group();
  scanPlatform.name = 'scanPlatform';
  scanPlatform.position.set(3.05, 0.45, -0.42);
  scanPlatform.rotation.set(0, deg(-20), 0);
  probe.add(scanPlatform);
  const platform = new THREE.Mesh(new THREE.BoxGeometry(0.55, 0.42, 0.5), foilMat);
  platform.name = 'platform';
  scanPlatform.add(platform);
  const narrowAngleCam = new THREE.Mesh(new THREE.CylinderGeometry(0.11, 0.11, 0.55, 8), metalMat);
  narrowAngleCam.name = 'narrowAngleCam';
  narrowAngleCam.position.set(-0.12, 0.3, 0.2);
  narrowAngleCam.rotation.set(deg(90), 0, 0);
  scanPlatform.add(narrowAngleCam);
  const narrowLens = new THREE.Mesh(new THREE.CylinderGeometry(0.075, 0.075, 0.03, 8), lensMat);
  narrowLens.name = 'narrowLens';
  narrowLens.position.set(-0.12, 0.3, 0.48);
  narrowLens.rotation.set(deg(90), 0, 0);
  scanPlatform.add(narrowLens);
  const wideAngleCam = new THREE.Mesh(new THREE.CylinderGeometry(0.08, 0.08, 0.32, 8), metalMat);
  wideAngleCam.name = 'wideAngleCam';
  wideAngleCam.position.set(0.16, 0.28, 0.16);
  wideAngleCam.rotation.set(deg(90), 0, 0);
  scanPlatform.add(wideAngleCam);
  const wideLens = new THREE.Mesh(new THREE.CylinderGeometry(0.055, 0.055, 0.03, 8), lensMat);
  wideLens.name = 'wideLens';
  wideLens.position.set(0.16, 0.28, 0.33);
  wideLens.rotation.set(deg(90), 0, 0);
  scanPlatform.add(wideLens);
  const spectrometer = new THREE.Mesh(new THREE.BoxGeometry(0.22, 0.16, 0.22), metalMat);
  spectrometer.name = 'spectrometer';
  spectrometer.position.set(0.12, -0.24, 0.12);
  scanPlatform.add(spectrometer);
  const platformLight = new THREE.Mesh(new THREE.BoxGeometry(0.08, 0.05, 0.02), glowMat);
  platformLight.name = 'platformLight';
  platformLight.position.set(-0.1, 0.05, 0.26);
  scanPlatform.add(platformLight);
  const magnetometerBoom = new THREE.Mesh(new THREE.CylinderGeometry(0.03, 0.05, 4.0162, 4), metalMat);
  magnetometerBoom.name = 'magnetometerBoom';
  magnetometerBoom.position.set(-0.825, 2.618, -0.92);
  magnetometerBoom.rotation.set(deg(-11.4947), deg(-1.6872), deg(16.6462));
  probe.add(magnetometerBoom);
  const cylinder55 = new THREE.Mesh(cylinderGeo4, darkMat);
  cylinder55.position.set(-0.48, 1.4888, -0.68);
  cylinder55.rotation.set(deg(-11.4947), deg(-1.6872), deg(16.6462));
  probe.add(cylinder55);
  const cylinder56 = new THREE.Mesh(cylinderGeo4, darkMat);
  cylinder56.position.set(-0.71, 2.2416, -0.84);
  cylinder56.rotation.set(deg(-11.4947), deg(-1.6872), deg(16.6462));
  probe.add(cylinder56);
  const cylinder57 = new THREE.Mesh(cylinderGeo4, darkMat);
  cylinder57.position.set(-0.94, 2.9944, -1);
  cylinder57.rotation.set(deg(-11.4947), deg(-1.6872), deg(16.6462));
  probe.add(cylinder57);
  const cylinder58 = new THREE.Mesh(cylinderGeo4, darkMat);
  cylinder58.position.set(-1.17, 3.7472, -1.16);
  cylinder58.rotation.set(deg(-11.4947), deg(-1.6872), deg(16.6462));
  probe.add(cylinder58);
  const magnetometer = new THREE.Mesh(new THREE.BoxGeometry(0.18, 0.18, 0.18), foilMat);
  magnetometer.name = 'magnetometer';
  magnetometer.position.set(-1.4, 4.5, -1.32);
  probe.add(magnetometer);
  const whipL = new THREE.Mesh(cylinderGeo5, metalMat);
  whipL.name = 'whipL';
  whipL.position.set(-1.125, -2.46, -0.77);
  whipL.rotation.set(deg(-8.4438), deg(-29.8825), deg(149.0735));
  probe.add(whipL);
  const whipR = new THREE.Mesh(cylinderGeo5, metalMat);
  whipR.name = 'whipR';
  whipR.position.set(1.125, -2.46, -0.77);
  whipR.rotation.set(deg(-8.4438), deg(29.8825), deg(-149.0735));
  probe.add(whipR);

  root.traverse((o) => {
    if (o.isMesh) {
      o.castShadow = true;
      o.receiveShadow = true;
    }
  });
  return root;
}

export default createSpaceProbe;

Avaliações e comentários

—
Nenhuma avaliação ainda — seja o primeiro.
5
0
4
0
3
0
2
0
1
0

Entre para avaliar e comentar.

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