Working version
15
.eslintrc.cjs
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
module.exports = {
|
||||
env: { browser: true, es2020: true },
|
||||
extends: [
|
||||
'eslint:recommended',
|
||||
'plugin:react/recommended',
|
||||
'plugin:react/jsx-runtime',
|
||||
'plugin:react-hooks/recommended',
|
||||
],
|
||||
parserOptions: { ecmaVersion: 'latest', sourceType: 'module' },
|
||||
settings: { react: { version: '18.2' } },
|
||||
plugins: ['react-refresh'],
|
||||
rules: {
|
||||
'react-refresh/only-export-components': 'warn',
|
||||
},
|
||||
}
|
||||
24
.gitignore
vendored
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
# Logs
|
||||
logs
|
||||
*.log
|
||||
npm-debug.log*
|
||||
yarn-debug.log*
|
||||
yarn-error.log*
|
||||
pnpm-debug.log*
|
||||
lerna-debug.log*
|
||||
|
||||
node_modules
|
||||
dist
|
||||
dist-ssr
|
||||
*.local
|
||||
|
||||
# Editor directories and files
|
||||
.vscode/*
|
||||
!.vscode/extensions.json
|
||||
.idea
|
||||
.DS_Store
|
||||
*.suo
|
||||
*.ntvs*
|
||||
*.njsproj
|
||||
*.sln
|
||||
*.sw?
|
||||
BIN
img/4k-ga95967816_1920.jpg
Normal file
|
After Width: | Height: | Size: 940 KiB |
BIN
img/back.png
Normal file
|
After Width: | Height: | Size: 93 KiB |
BIN
img/bottom.png
Normal file
|
After Width: | Height: | Size: 95 KiB |
BIN
img/cubemap.png
Normal file
|
After Width: | Height: | Size: 726 KiB |
BIN
img/earth/6k_earth_clouds.jpg
Normal file
|
After Width: | Height: | Size: 12 MiB |
BIN
img/earth/6k_earth_daymap.jpg
Normal file
|
After Width: | Height: | Size: 7.9 MiB |
BIN
img/earth/6k_earth_nightmap.jpg
Normal file
|
After Width: | Height: | Size: 3.1 MiB |
BIN
img/earth/6k_earth_normal_map.jpg
Normal file
|
After Width: | Height: | Size: 6.2 MiB |
BIN
img/earth/6k_earth_specular_map.jpg
Normal file
|
After Width: | Height: | Size: 6.1 MiB |
BIN
img/earth/earth_bump_1k.jpg
Normal file
|
After Width: | Height: | Size: 89 KiB |
BIN
img/earth/earth_clouds_color_1k.jpg
Normal file
|
After Width: | Height: | Size: 230 KiB |
BIN
img/earth/earth_clouds_trans_1k.jpg
Normal file
|
After Width: | Height: | Size: 180 KiB |
BIN
img/earth/earth_night_uv_1k.jpg
Normal file
|
After Width: | Height: | Size: 83 KiB |
BIN
img/earth/earth_spec_1k.jpg
Normal file
|
After Width: | Height: | Size: 114 KiB |
BIN
img/earth/earth_uv.jpg
Normal file
|
After Width: | Height: | Size: 3.3 MiB |
BIN
img/earth/earth_uv_10k.jpg
Normal file
|
After Width: | Height: | Size: 11 MiB |
BIN
img/earth/earth_uv_1k.jpg
Normal file
|
After Width: | Height: | Size: 336 KiB |
BIN
img/front.png
Normal file
|
After Width: | Height: | Size: 94 KiB |
BIN
img/jupiter/jupiter2_1k.jpg
Normal file
|
After Width: | Height: | Size: 140 KiB |
BIN
img/jupiter/jupiter2_2k.jpg
Normal file
|
After Width: | Height: | Size: 308 KiB |
BIN
img/jupiter/jupiter2_4k.jpg
Normal file
|
After Width: | Height: | Size: 841 KiB |
BIN
img/jupiter/jupiter2_6k.jp2
Normal file
BIN
img/left.png
Normal file
|
After Width: | Height: | Size: 96 KiB |
BIN
img/mars/mars_1k_color.jpg
Normal file
|
After Width: | Height: | Size: 227 KiB |
BIN
img/mars/mars_1k_normal.jpg
Normal file
|
After Width: | Height: | Size: 45 KiB |
BIN
img/mars/mars_1k_topo.jpg
Normal file
|
After Width: | Height: | Size: 91 KiB |
BIN
img/mercury/mercurybump.jpg
Normal file
|
After Width: | Height: | Size: 190 KiB |
BIN
img/mercury/mercurymap.jpg
Normal file
|
After Width: | Height: | Size: 279 KiB |
BIN
img/moon/moonbump1k.jpg
Normal file
|
After Width: | Height: | Size: 377 KiB |
BIN
img/moon/moonbump2k.jpg
Normal file
|
After Width: | Height: | Size: 997 KiB |
BIN
img/moon/moonbump4k.jpg
Normal file
|
After Width: | Height: | Size: 2.6 MiB |
BIN
img/moon/moonmap1k.jpg
Normal file
|
After Width: | Height: | Size: 394 KiB |
BIN
img/moon/moonmap2k.jpg
Normal file
|
After Width: | Height: | Size: 1.5 MiB |
BIN
img/moon/moonmap4k.jpg
Normal file
|
After Width: | Height: | Size: 5.7 MiB |
BIN
img/neptune/neptunemap.jpg
Normal file
|
After Width: | Height: | Size: 47 KiB |
|
|
@ -0,0 +1 @@
|
|||
,denis,arch,06.12.2022 09:42,file:///home/denis/.config/libreoffice/4;
|
||||
BIN
img/pluto/8_Krankenhausmanagement_final_vertont.pptx
Normal file
BIN
img/pluto/plutobump1k.jpg
Normal file
|
After Width: | Height: | Size: 222 KiB |
BIN
img/pluto/plutobump2k.jpg
Normal file
|
After Width: | Height: | Size: 573 KiB |
BIN
img/pluto/plutomap1k.jpg
Normal file
|
After Width: | Height: | Size: 318 KiB |
BIN
img/pluto/plutomap2k.jpg
Normal file
|
After Width: | Height: | Size: 1 MiB |
BIN
img/right.png
Normal file
|
After Width: | Height: | Size: 95 KiB |
BIN
img/saturn/saturnmap.jpg
Normal file
|
After Width: | Height: | Size: 69 KiB |
BIN
img/saturn/saturnringcolor.jpg
Normal file
|
After Width: | Height: | Size: 9.1 KiB |
BIN
img/saturn/saturnringpattern.gif
Normal file
|
After Width: | Height: | Size: 27 KiB |
BIN
img/skybox.zip
Normal file
BIN
img/skybox/back.png
Normal file
|
After Width: | Height: | Size: 176 KiB |
BIN
img/skybox/bottom.png
Normal file
|
After Width: | Height: | Size: 177 KiB |
BIN
img/skybox/cubemap.png
Normal file
|
After Width: | Height: | Size: 1.3 MiB |
BIN
img/skybox/front.png
Normal file
|
After Width: | Height: | Size: 177 KiB |
BIN
img/skybox/left.png
Normal file
|
After Width: | Height: | Size: 177 KiB |
BIN
img/skybox/right.png
Normal file
|
After Width: | Height: | Size: 176 KiB |
BIN
img/skybox/top.png
Normal file
|
After Width: | Height: | Size: 175 KiB |
BIN
img/sun/sun_uv.jpg
Normal file
|
After Width: | Height: | Size: 275 KiB |
BIN
img/top.png
Normal file
|
After Width: | Height: | Size: 93 KiB |
BIN
img/uranus/uranusmap.jpg
Normal file
|
After Width: | Height: | Size: 8.7 KiB |
BIN
img/uranus/uranusringcolour.jpg
Normal file
|
After Width: | Height: | Size: 6.5 KiB |
BIN
img/uranus/uranusringtrans.gif
Normal file
|
After Width: | Height: | Size: 41 KiB |
BIN
img/venus/venusbump.jpg
Normal file
|
After Width: | Height: | Size: 246 KiB |
BIN
img/venus/venusmap.jpg
Normal file
|
After Width: | Height: | Size: 249 KiB |
10
index.html
Normal file
|
|
@ -0,0 +1,10 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<title>Why no working</title>
|
||||
</head>
|
||||
<body>
|
||||
<div id="root"></div>
|
||||
<script type="module" src="/src/App.jsx"></script>
|
||||
</body>
|
||||
</html>
|
||||
66
js/earth/earth_mesh.js
Normal file
|
|
@ -0,0 +1,66 @@
|
|||
import * as THREE from "three";
|
||||
import { moonMesh } from "../moon/moon.js";
|
||||
|
||||
const textL = new THREE.TextureLoader();
|
||||
|
||||
const r = 25;
|
||||
const s = 50;
|
||||
const tilt = 1;
|
||||
|
||||
const material = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/earth/earth_uv_1k.jpg"),
|
||||
bumpMap: textL.load("../../img/earth/earth_bump_1k.jpg"),
|
||||
specularMap: textL.load("../../img/earth/earth_spec_1k.jpg"),
|
||||
bumpScale: 0.2,
|
||||
shininess: 0.5,
|
||||
});
|
||||
|
||||
const earthMesh = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(6371.0 / 6000, 50, 50),
|
||||
material
|
||||
);
|
||||
|
||||
earthMesh.rotation.z = tilt;
|
||||
|
||||
earthMesh.name = "earthMesh";
|
||||
|
||||
const cloudGeometry = new THREE.SphereGeometry(6371.0 / 6000 + 0.01, 50, 50);
|
||||
const cloudMaterial = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/earth/6k_earth_clouds.jpg"),
|
||||
transparent: true,
|
||||
opacity: 0.5,
|
||||
});
|
||||
|
||||
const clouds = new THREE.Mesh(cloudGeometry, cloudMaterial);
|
||||
clouds.rotation.z = tilt;
|
||||
|
||||
const axisPoints = [
|
||||
new THREE.Vector3(0, 6371.0 / 6000 + 0.5, 0),
|
||||
new THREE.Vector3(0, -(6371.0 / 6000 + 0.5), 0),
|
||||
];
|
||||
const axisGeometry = new THREE.BufferGeometry().setFromPoints(axisPoints);
|
||||
const axis = new THREE.Line(
|
||||
axisGeometry,
|
||||
new THREE.LineBasicMaterial({
|
||||
color: 0x330000,
|
||||
transparent: true,
|
||||
opacity: 0.5,
|
||||
linewidth: 2,
|
||||
})
|
||||
);
|
||||
axis.rotation.z = 0;
|
||||
|
||||
//earthMesh.castShadow = true;
|
||||
//earthMesh.receiveShadow = true;
|
||||
//clouds.receiveShadow = true;
|
||||
|
||||
const earthGroup = new THREE.Group();
|
||||
moonMesh.position.set(0, 384000 / 200000, 0);
|
||||
earthGroup.userData.id = 399;
|
||||
earthGroup.name = "earthGroup";
|
||||
earthGroup.add(earthMesh);
|
||||
earthGroup.add(clouds);
|
||||
earthGroup.add(axis);
|
||||
earthGroup.add(moonMesh);
|
||||
|
||||
export { earthMesh, earthGroup };
|
||||
21
js/jupiter/jupiter.js
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
import * as THREE from "three";
|
||||
|
||||
const textL = new THREE.TextureLoader();
|
||||
|
||||
const material = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/jupiter/jupiter2_4k.jpg"),
|
||||
});
|
||||
|
||||
const jupiterMesh = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(69911 / 6000, 50, 50),
|
||||
material
|
||||
);
|
||||
|
||||
jupiterMesh.name = "jupiterMesh";
|
||||
|
||||
const jupiterGroup = new THREE.Group();
|
||||
jupiterGroup.name = "jupiterGroup";
|
||||
jupiterGroup.userData.id = 599;
|
||||
jupiterGroup.add(jupiterMesh);
|
||||
|
||||
export { jupiterMesh, jupiterGroup };
|
||||
23
js/mars/mars.js
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
import * as THREE from "three";
|
||||
|
||||
const textL = new THREE.TextureLoader();
|
||||
|
||||
const material = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/mars/mars_1k_color.jpg"),
|
||||
bumpMap: textL.load("../../img/mars/mars_1k_topo.jpg"),
|
||||
normalMap: textL.load("../../img/mars/mars_1k_normal.jpg"),
|
||||
});
|
||||
|
||||
const marsMesh = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(3389.5 / 6000, 50, 50),
|
||||
material
|
||||
);
|
||||
|
||||
marsMesh.name = "mercuryMesh";
|
||||
|
||||
const marsGroup = new THREE.Group();
|
||||
marsGroup.name = "marsGroup";
|
||||
marsGroup.userData.id = 499;
|
||||
marsGroup.add(marsMesh);
|
||||
|
||||
export { marsMesh, marsGroup };
|
||||
22
js/mercury/mercury.js
Normal file
|
|
@ -0,0 +1,22 @@
|
|||
import * as THREE from "three";
|
||||
|
||||
const textL = new THREE.TextureLoader();
|
||||
|
||||
const material = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/mercury/mercurymap.jpg"),
|
||||
bumpMap: textL.load("../../img/mercury/mercurybump.jpg"),
|
||||
});
|
||||
|
||||
const mercuryMesh = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(2439.7 / 6000, 50, 50),
|
||||
material
|
||||
);
|
||||
|
||||
mercuryMesh.name = "mercuryMesh";
|
||||
|
||||
const mercuryGroup = new THREE.Group();
|
||||
mercuryGroup.name = "mercuryGroup";
|
||||
mercuryGroup.userData.id = 199;
|
||||
mercuryGroup.add(mercuryMesh);
|
||||
|
||||
export { mercuryMesh, mercuryGroup };
|
||||
19
js/moon/moon.js
Normal file
|
|
@ -0,0 +1,19 @@
|
|||
import * as THREE from "three";
|
||||
|
||||
const textL = new THREE.TextureLoader();
|
||||
|
||||
const r = 1737 / 6000;
|
||||
const s = 50;
|
||||
|
||||
const moonMaterial = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/moon/moonmap4k.jpg"),
|
||||
bumpMap: textL.load("../../img/moon/moonbump4k.jpg"),
|
||||
bumpScale: 0.2,
|
||||
});
|
||||
|
||||
const moonMesh = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(r, s, s),
|
||||
moonMaterial
|
||||
);
|
||||
|
||||
export { moonMesh };
|
||||
21
js/neptune/neptune.js
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
import * as THREE from "three";
|
||||
|
||||
const textL = new THREE.TextureLoader();
|
||||
|
||||
const material = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/neptune/neptunemap.jpg"),
|
||||
});
|
||||
|
||||
const neptuneMesh = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(24622 / 6000, 50, 50),
|
||||
material
|
||||
);
|
||||
|
||||
neptuneMesh.name = "neptuneMesh";
|
||||
|
||||
const neptuneGroup = new THREE.Group();
|
||||
neptuneGroup.name = "neptuneGroup";
|
||||
neptuneGroup.userData.id = 899;
|
||||
neptuneGroup.add(neptuneMesh);
|
||||
|
||||
export { neptuneMesh, neptuneGroup };
|
||||
21
js/pluto/pluto.js
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
import * as THREE from "three";
|
||||
|
||||
const textL = new THREE.TextureLoader();
|
||||
|
||||
const material = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/pluto/plutomap2k.jpg"),
|
||||
bumpMap: textL.load("../../img/pluto/plutobump2k.jpg"),
|
||||
});
|
||||
|
||||
const plutoMesh = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(1188 / 6000, 50, 50),
|
||||
material
|
||||
);
|
||||
|
||||
plutoMesh.name = "plutoMesh";
|
||||
|
||||
const plutoGroup = new THREE.Group();
|
||||
plutoGroup.name = "plutoGroup";
|
||||
plutoGroup.add(plutoMesh);
|
||||
|
||||
export { plutoMesh, plutoGroup };
|
||||
87
js/saturn/saturn.js
Normal file
|
|
@ -0,0 +1,87 @@
|
|||
import * as THREE from "three";
|
||||
import { BoxGeometry } from "three";
|
||||
|
||||
const textL = new THREE.TextureLoader();
|
||||
|
||||
const material = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/saturn/saturnmap.jpg"),
|
||||
});
|
||||
|
||||
const saturnMesh = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(58232 / 6000, 30, 30),
|
||||
material
|
||||
);
|
||||
|
||||
saturnMesh.name = "saturnMesh";
|
||||
|
||||
const sringGeo = new THREE.RingGeometry(
|
||||
58232 / 6000 + 1,
|
||||
58232 / 6000 + 5,
|
||||
100,
|
||||
100
|
||||
);
|
||||
|
||||
const textured = textL.load("../../img/saturn/saturnringcolor.jpg");
|
||||
const otexture = textL.load("../../img/saturn/saturnringpattern.gif");
|
||||
|
||||
const sringMaterial = new THREE.ShaderMaterial({
|
||||
uniforms: {
|
||||
texturea: { value: textured },
|
||||
alphaTex: { value: otexture },
|
||||
innerRadius: { value: 58232 / 6000 + 0 },
|
||||
outerRadius: { value: 58232 / 6000 + 0 },
|
||||
},
|
||||
vertexShader: `
|
||||
varying vec3 vPos;
|
||||
|
||||
void main() {
|
||||
vPos = position;
|
||||
vec3 viewPosition = (modelViewMatrix * vec4(position, 1.)).xyz;
|
||||
gl_Position = projectionMatrix * vec4(viewPosition, 1.);
|
||||
}
|
||||
`,
|
||||
fragmentShader: `
|
||||
uniform sampler2D texturea;
|
||||
uniform sampler2D alphaTex;
|
||||
uniform float innerRadius;
|
||||
uniform float outerRadius;
|
||||
|
||||
varying vec3 vPos;
|
||||
|
||||
vec4 color() {
|
||||
vec2 uv = vec2(0);
|
||||
uv.x = (length(vPos) - innerRadius) / (innerRadius + outerRadius);
|
||||
|
||||
vec4 pixel = texture2D(texturea, uv);
|
||||
vec4 pixel2 = texture2D(alphaTex, uv);
|
||||
pixel[3] = pixel2[0];
|
||||
if (pixel[3] <= 0.01) {
|
||||
discard;
|
||||
}
|
||||
return pixel;
|
||||
}
|
||||
|
||||
void main() {
|
||||
gl_FragColor = color();
|
||||
}
|
||||
`,
|
||||
transparent: true,
|
||||
side: THREE.DoubleSide,
|
||||
});
|
||||
|
||||
const sringMat = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/saturn/saturnringcolor.jpg"),
|
||||
alphaMap: textL.load("../../img/saturn/saturnringpattern.gif"),
|
||||
side: THREE.DoubleSide,
|
||||
transparent: true,
|
||||
});
|
||||
|
||||
const sringMesh = new THREE.Mesh(sringGeo, sringMaterial);
|
||||
|
||||
const saturnGroup = new THREE.Group();
|
||||
saturnGroup.name = "saturnGroup";
|
||||
saturnGroup.userData.id = 699;
|
||||
saturnGroup.add(saturnMesh);
|
||||
saturnGroup.add(sringMesh);
|
||||
|
||||
export { saturnMesh, saturnGroup };
|
||||
17
js/skybox/skybox.js
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
import * as THREE from "three"
|
||||
|
||||
const textL = new THREE.CubeTextureLoader();
|
||||
|
||||
//const skyboxGeo = new THREE.BoxGeometry(10000,10000,10000);
|
||||
//const skybox = new THREE.Mesh(skyboxGeo);
|
||||
|
||||
const skybox = textL.load([
|
||||
"../img/skybox/front.png",
|
||||
"../img/skybox/back.png",
|
||||
"../img/skybox/top.png",
|
||||
"../img/skybox/bottom.png",
|
||||
"../img/skybox/left.png",
|
||||
"../img/skybox/right.png"
|
||||
])
|
||||
|
||||
export default skybox
|
||||
22
js/sun/sun_mesh.js
Normal file
|
|
@ -0,0 +1,22 @@
|
|||
import * as THREE from "three";
|
||||
|
||||
const standardSunMaterial = new THREE.MeshStandardMaterial({
|
||||
emissive: 0xffd700,
|
||||
emissiveMap: new THREE.TextureLoader().load("./img/sun/sun_uv.jpg"),
|
||||
emissiveIntensity: 1,
|
||||
});
|
||||
|
||||
const sunMesh = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(10000 / 6000, 30, 30),
|
||||
standardSunMaterial
|
||||
);
|
||||
|
||||
sunMesh.name = "sunMesh";
|
||||
|
||||
var sunLight = new THREE.PointLight(0xffffff, 1, 10000.0, 2);
|
||||
const sunGroup = new THREE.Group();
|
||||
sunGroup.name = "Sun";
|
||||
sunGroup.add(sunMesh);
|
||||
//sunGroup.add(sunLight);
|
||||
|
||||
export { sunGroup, sunMesh };
|
||||
21
js/uranus/uranus.js
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
import * as THREE from "three";
|
||||
|
||||
const textL = new THREE.TextureLoader();
|
||||
|
||||
const material = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/uranus/uranusmap.jpg"),
|
||||
});
|
||||
|
||||
const uranusMesh = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(25362 / 6000, 50, 50),
|
||||
material
|
||||
);
|
||||
|
||||
uranusMesh.name = "uranusMesh";
|
||||
|
||||
const uranusGroup = new THREE.Group();
|
||||
uranusGroup.name = "uranusGroup";
|
||||
uranusGroup.userData.id = 799;
|
||||
uranusGroup.add(uranusMesh);
|
||||
|
||||
export { uranusMesh, uranusGroup };
|
||||
23
js/venus/venus.js
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
import * as THREE from "three";
|
||||
|
||||
const textL = new THREE.TextureLoader();
|
||||
|
||||
const material = new THREE.MeshPhongMaterial({
|
||||
map: textL.load("../../img/venus/venusmap.jpg"),
|
||||
bumpMap: textL.load("../../img/venus/venusbump.jpg"),
|
||||
bumpScale: 0.2,
|
||||
});
|
||||
|
||||
const venusMesh = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(6051.8 / 6000, 30, 30),
|
||||
material
|
||||
);
|
||||
|
||||
venusMesh.name = "venusMesh";
|
||||
|
||||
const venusGroup = new THREE.Group();
|
||||
venusGroup.name = "venusGroup";
|
||||
venusGroup.userData.id = 299;
|
||||
venusGroup.add(venusMesh);
|
||||
|
||||
export { venusMesh, venusGroup };
|
||||
379
nbody.js
Normal file
|
|
@ -0,0 +1,379 @@
|
|||
import * as THREE from "three";
|
||||
import { earthMesh, earthGroup } from "./js/earth/earth_mesh.js";
|
||||
import { sunMesh, sunGroup } from "./js/sun/sun_mesh.js";
|
||||
import { venusMesh, venusGroup } from "./js/venus/venus.js";
|
||||
import { mercuryMesh, mercuryGroup } from "./js/mercury/mercury.js";
|
||||
import { marsMesh, marsGroup } from "./js/mars/mars.js";
|
||||
import { saturnMesh, saturnGroup } from "./js/saturn/saturn.js";
|
||||
import { jupiterMesh, jupiterGroup } from "./js/jupiter/jupiter.js";
|
||||
import { uranusMesh, uranusGroup } from "./js/uranus/uranus.js";
|
||||
import { neptuneMesh, neptuneGroup } from "./js/neptune/neptune.js";
|
||||
import { plutoMesh, plutoGroup } from "./js/pluto/pluto.js";
|
||||
import skybox from "./js/skybox/skybox.js";
|
||||
import { ArcballControls } from "three/addons/controls/ArcballControls";
|
||||
import { OrbitControls } from "three/addons/controls/OrbitControls";
|
||||
import { BufferAttribute, BufferGeometryLoader, Color, Vector3 } from "three";
|
||||
import axios from "axios";
|
||||
import { EffectComposer } from "three/addons/postprocessing/EffectComposer.js";
|
||||
import { RenderPass } from "three/addons/postprocessing/RenderPass.js";
|
||||
import { OutlinePass } from "three/addons/postprocessing/OutlinePass.js";
|
||||
import { ShaderPass } from "three/addons/postprocessing/ShaderPass.js";
|
||||
import { FXAAShader } from "three/addons/shaders/FXAAShader.js";
|
||||
import { GlitchPass } from "three/addons/postprocessing/GlitchPass.js";
|
||||
import { UnrealBloomPass } from "three/addons/postprocessing/UnrealBloomPass.js";
|
||||
import { PointLight } from "three";
|
||||
//import { data } from "./orbitcalculations.js";
|
||||
|
||||
var objectsToOutline = [];
|
||||
|
||||
let selectedObjects = [];
|
||||
|
||||
var distanceScaleFactor = 10000000;
|
||||
|
||||
document.body.style.margin = 0;
|
||||
|
||||
var clock = new THREE.Clock();
|
||||
var delta = 0;
|
||||
|
||||
const scene = new THREE.Scene();
|
||||
|
||||
const axesHelper = new THREE.AxesHelper(1000);
|
||||
scene.add(axesHelper);
|
||||
|
||||
scene.add(earthGroup);
|
||||
earthGroup.position.setX(149598262.0 / 1000);
|
||||
scene.add(sunGroup);
|
||||
scene.add(venusGroup);
|
||||
venusGroup.position.setX(108209475.0 / 1000);
|
||||
scene.add(mercuryGroup);
|
||||
mercuryGroup.position.setX(57909227.0 / 1000);
|
||||
scene.add(jupiterGroup);
|
||||
jupiterGroup.position.setX(778340821.0 / 1000);
|
||||
scene.add(saturnGroup);
|
||||
saturnGroup.position.setX(1426666422.0 / 1000);
|
||||
scene.add(uranusGroup);
|
||||
uranusGroup.position.setX(2870658186.0 / 1000);
|
||||
scene.add(marsGroup);
|
||||
marsGroup.position.setX(227943842.0 / 1000);
|
||||
scene.add(neptuneGroup);
|
||||
neptuneGroup.position.setX(4498396441.0 / 1000);
|
||||
|
||||
scene.background = skybox;
|
||||
|
||||
const camera = new THREE.PerspectiveCamera(
|
||||
75,
|
||||
innerWidth / innerHeight,
|
||||
0.1,
|
||||
1000000000
|
||||
);
|
||||
camera.position.z = 40;
|
||||
//camera.useQuaternion = true;
|
||||
|
||||
const renderer = new THREE.WebGLRenderer({ alpha: false });
|
||||
renderer.setPixelRatio(devicePixelRatio);
|
||||
renderer.setSize(innerWidth, innerHeight);
|
||||
//renderer.setClearColor(0x222222, 0.0);
|
||||
renderer.shadowMap.enabled = true;
|
||||
document.body.appendChild(renderer.domElement);
|
||||
renderer.autoClear = false;
|
||||
//var arc = new ArcballControls(camera, renderer.domElement, scene);
|
||||
|
||||
const controls = new OrbitControls(camera, renderer.domElement);
|
||||
|
||||
var planetGroups = [
|
||||
mercuryGroup,
|
||||
venusGroup,
|
||||
earthGroup,
|
||||
marsGroup,
|
||||
jupiterGroup,
|
||||
saturnGroup,
|
||||
uranusGroup,
|
||||
neptuneGroup,
|
||||
];
|
||||
|
||||
var meshes = [];
|
||||
planetGroups.forEach((planet) => {
|
||||
meshes.push(planet.children[0]);
|
||||
});
|
||||
console.log(meshes);
|
||||
|
||||
const color = 0xffffff;
|
||||
const intensity = 1;
|
||||
const light = new THREE.AmbientLight(color, intensity);
|
||||
scene.add(light);
|
||||
|
||||
var composer = new EffectComposer(renderer);
|
||||
|
||||
var renderPass = new RenderPass(scene, camera);
|
||||
|
||||
const bloomPass = new UnrealBloomPass(
|
||||
new THREE.Vector2(window.innerWidth, window.innerHeight, 1.5, 0.4, 0.85)
|
||||
);
|
||||
|
||||
bloomPass.threshold = 0;
|
||||
bloomPass.strength = 5;
|
||||
bloomPass.radius = 0;
|
||||
|
||||
var outlinePass = new OutlinePass(
|
||||
new THREE.Vector2(window.innerWidth, window.innerHeight),
|
||||
scene,
|
||||
camera
|
||||
);
|
||||
|
||||
outlinePass.renderToScreen = true;
|
||||
composer.addPass(renderPass);
|
||||
composer.addPass(outlinePass);
|
||||
//composer.addPass(bloomPass);
|
||||
|
||||
var effectFXAA = new ShaderPass(FXAAShader);
|
||||
effectFXAA.uniforms["resolution"].value.set(
|
||||
1 / window.innerWidth,
|
||||
1 / window.innerHeight
|
||||
);
|
||||
effectFXAA.renderToScreen = true;
|
||||
composer.addPass(effectFXAA);
|
||||
|
||||
/*var effectFXAA = new ShaderPass(THREE.FXAAShader);
|
||||
effectFXAA.uniforms["resolution"].value.set(
|
||||
1 / window.innerWidth,
|
||||
1 / window.innerHeight
|
||||
);
|
||||
effectFXAA.renderToScreen = true;
|
||||
composer.addPass(effectFXAA);*/
|
||||
|
||||
var params = {
|
||||
edgeStrength: 10.0,
|
||||
edgeGlow: 1.0,
|
||||
edgeThickness: 1.0,
|
||||
pulsePeriod: 0,
|
||||
rotate: true,
|
||||
usePatternTexture: false,
|
||||
};
|
||||
outlinePass.edgeStrength = params.edgeStrength;
|
||||
outlinePass.edgeGlow = params.edgeGlow;
|
||||
outlinePass.visibleEdgeColor.set(0xffffff);
|
||||
outlinePass.hiddenEdgeColor.set(0xffffff);
|
||||
|
||||
const raycaster = new THREE.Raycaster();
|
||||
const pointer = new THREE.Vector2();
|
||||
/*const phongMaterial = new THREE.MeshPhongMaterial({
|
||||
color: 0xffffff,
|
||||
specular: 0x111111,
|
||||
shininess: 5,
|
||||
});
|
||||
const test = new THREE.Mesh(
|
||||
new THREE.SphereGeometry(6371.0, 50, 50),
|
||||
phongMaterial
|
||||
);
|
||||
test.position.add(new THREE.Vector3(100000, 100000, 100000));
|
||||
scene.add(test);*/
|
||||
let lines = [];
|
||||
planetGroups.forEach((planet) => {
|
||||
const lineGeometry = new THREE.BufferGeometry();
|
||||
const lineMaterial = new THREE.LineBasicMaterial({ color: 0xffffff });
|
||||
const line = new THREE.Line(lineGeometry, lineMaterial);
|
||||
lineGeometry.setAttribute(
|
||||
"position",
|
||||
new THREE.BufferAttribute(new Float32Array([]), 3)
|
||||
);
|
||||
lineGeometry.setAttribute(
|
||||
"normal",
|
||||
new THREE.BufferAttribute(new Float32Array([]), 3)
|
||||
);
|
||||
line.geometry.attributes.position.needsUpdate = true;
|
||||
scene.add(line);
|
||||
planet.userData["line"] = line;
|
||||
});
|
||||
console.log(lines);
|
||||
|
||||
//renderer.shadowMap.enabled = true;
|
||||
//light.castShadow = true;
|
||||
//light.shadow.mapSize.width = 512;
|
||||
//light.shadow.mapSize.height = 512;
|
||||
//light.shadow.camera.near = 150;
|
||||
//light.shadow.camera.far = 350;
|
||||
|
||||
var obj = null;
|
||||
function onPointerDown(event) {
|
||||
// calculate pointer position in normalized device coordinates
|
||||
// (-1 to +1) for both components
|
||||
|
||||
pointer.x = (event.clientX / window.innerWidth) * 2 - 1;
|
||||
pointer.y = -(event.clientY / window.innerHeight) * 2 + 1;
|
||||
|
||||
raycaster.setFromCamera(pointer, camera);
|
||||
// calculate objects intersecting the picking ray
|
||||
const intersects = raycaster.intersectObjects(planetGroups);
|
||||
for (let i = 0; i < intersects.length; i++) {
|
||||
obj = intersects[i].object.parent;
|
||||
}
|
||||
if (event.button == 0 && obj) {
|
||||
controls.target.copy(obj.position);
|
||||
controls.minDistance = obj.children[0].geometry.boundingSphere.radius * 1.5;
|
||||
controls.maxDistance = obj.children[0].geometry.boundingSphere.radius * 10;
|
||||
controls.update();
|
||||
}
|
||||
if (event.button == 2) {
|
||||
obj = null;
|
||||
controls.minDistance = 1;
|
||||
controls.maxDistance = Infinity;
|
||||
}
|
||||
}
|
||||
|
||||
function onPointerMove(event) {
|
||||
// calculate pointer position in normalized device coordinates
|
||||
// (-1 to +1) for both components
|
||||
|
||||
pointer.x = (event.clientX / window.innerWidth) * 2 - 1;
|
||||
pointer.y = -(event.clientY / window.innerHeight) * 2 + 1;
|
||||
|
||||
// calculate objects intersecting the picking ray
|
||||
raycaster.setFromCamera(pointer, camera);
|
||||
|
||||
const intersects = raycaster.intersectObject(scene, true);
|
||||
|
||||
function addSelectedObject(object) {
|
||||
selectedObjects = [];
|
||||
selectedObjects.push(object);
|
||||
}
|
||||
|
||||
if (intersects.length > 0) {
|
||||
const selectedObject = intersects[0].object;
|
||||
addSelectedObject(selectedObject);
|
||||
outlinePass.selectedObjects = selectedObjects;
|
||||
} else {
|
||||
outlinePass.selectedObjects = [];
|
||||
}
|
||||
}
|
||||
|
||||
var url = "http://127.0.0.1:8000/duration";
|
||||
|
||||
var data;
|
||||
setInterval(
|
||||
await axios.get(url).then((res) => {
|
||||
data = res.data;
|
||||
console.log(data);
|
||||
}),
|
||||
10000
|
||||
);
|
||||
planetGroups.forEach((planet) => {
|
||||
planet.userData["positions"] = data[planet.userData.id];
|
||||
});
|
||||
function calculateOrbitLength() {
|
||||
planetGroups.forEach((planet) => {
|
||||
let length = 0;
|
||||
if (planet.name != "Sun") {
|
||||
for (let i = 0; i < planet.userData.positions.length - 1; i += 2) {
|
||||
const dx = Math.abs(
|
||||
planet.userData.positions[i + 1].x - planet.userData.positions[i].x
|
||||
);
|
||||
const dy = Math.abs(
|
||||
planet.userData.positions[i + 1].y - planet.userData.positions[i].y
|
||||
);
|
||||
const dz = Math.abs(
|
||||
planet.userData.positions[i + 1].z - planet.userData.positions[i].z
|
||||
);
|
||||
var segment = Math.sqrt(dx * dx + dy * dy + dz * dz);
|
||||
//console.log(
|
||||
// `dx: ${dx}, dy: ${dy}, dz: ${dz}, segmentLength: ${segment}`
|
||||
//);
|
||||
length += segment;
|
||||
}
|
||||
}
|
||||
planet.userData["orbitLength"] = length / distanceScaleFactor;
|
||||
console.log(
|
||||
planet.userData.orbitLength * distanceScaleFactor +
|
||||
" " +
|
||||
planet.userData.id
|
||||
);
|
||||
});
|
||||
}
|
||||
calculateOrbitLength();
|
||||
|
||||
function cutPath(line, maxLength) {
|
||||
const positions = line.geometry.attributes.position.array;
|
||||
var currLength = getLength(line);
|
||||
if (currLength > maxLength) {
|
||||
line.geometry.attributes.position.array = positions.slice(3);
|
||||
line.geometry.setDrawRange(
|
||||
0,
|
||||
line.geometry.attributes.position.array.length / 3
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
function getLength(line, maxLength) {
|
||||
var length = 0;
|
||||
const positions = line.geometry.attributes.position.array;
|
||||
for (let i = 0; i < positions.length - 6; i += 3) {
|
||||
const dx = positions[i + 3] - positions[i];
|
||||
const dy = positions[i + 4] - positions[i + 1];
|
||||
const dz = positions[i + 5] - positions[i + 2];
|
||||
length += Math.sqrt(dx * dx + dy * dy + dz * dz);
|
||||
}
|
||||
return length;
|
||||
}
|
||||
|
||||
var asdf = 0;
|
||||
var last = 0;
|
||||
function animate(now) {
|
||||
window.requestAnimationFrame(animate);
|
||||
renderer.render(scene, camera);
|
||||
controls.update();
|
||||
composer.render();
|
||||
|
||||
if (obj) {
|
||||
controls.target.copy(obj.position);
|
||||
}
|
||||
|
||||
planetGroups.forEach((planet) => {
|
||||
if (false) {
|
||||
if (planet.name != "Sun") {
|
||||
planet.position.set(
|
||||
Number(data[planet.userData.id].position.x / distanceScaleFactor),
|
||||
Number(data[planet.userData.id].position.y / distanceScaleFactor),
|
||||
Number(data[planet.userData.id].position.z / distanceScaleFactor)
|
||||
);
|
||||
}
|
||||
}
|
||||
if (planet.name != "Sun" && asdf < data["199"].length) {
|
||||
if (true) {
|
||||
const vertices =
|
||||
planet.userData.line.geometry.attributes.position.array;
|
||||
const newVertices = new Float32Array(vertices.length + 3);
|
||||
newVertices.set(vertices);
|
||||
newVertices.set(
|
||||
[
|
||||
Number(data[planet.userData.id][asdf].x / distanceScaleFactor),
|
||||
Number(data[planet.userData.id][asdf].y / distanceScaleFactor),
|
||||
Number(data[planet.userData.id][asdf].z / distanceScaleFactor),
|
||||
],
|
||||
vertices.length
|
||||
);
|
||||
planet.userData.line.geometry.setAttribute(
|
||||
"position",
|
||||
new THREE.BufferAttribute(newVertices, 3)
|
||||
);
|
||||
planet.userData["pathLength"] = getLength(planet.userData.line, 10);
|
||||
cutPath(planet.userData.line, planet.userData.orbitLength * 0.5);
|
||||
}
|
||||
planet.position.set(
|
||||
Number(data[planet.userData.id][asdf].x / distanceScaleFactor),
|
||||
Number(data[planet.userData.id][asdf].y / distanceScaleFactor),
|
||||
Number(data[planet.userData.id][asdf].z / distanceScaleFactor)
|
||||
);
|
||||
}
|
||||
});
|
||||
performance.now();
|
||||
earthGroup.children[0].rotation.y += 0.0015;
|
||||
earthGroup.children[1].rotation.y += 0.0025;
|
||||
earthGroup.children[3].position.y =
|
||||
(-Math.cos(0.001 * performance.now() * 1) * 384000) / 200000;
|
||||
earthGroup.children[3].position.z =
|
||||
(-Math.sin(0.001 * performance.now() * 1) * 384000) / 200000;
|
||||
asdf++;
|
||||
}
|
||||
animate();
|
||||
|
||||
window.addEventListener("pointermove", onPointerMove);
|
||||
window.addEventListener("pointerdown", onPointerDown);
|
||||
9419
package-lock.json
generated
Normal file
39
package.json
Normal file
|
|
@ -0,0 +1,39 @@
|
|||
{
|
||||
"name": "solar-system",
|
||||
"private": true,
|
||||
"version": "0.0.0",
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"dev": "vite",
|
||||
"build": "vite build",
|
||||
"lint": "eslint src --ext js,jsx --report-unused-disable-directives --max-warnings 0",
|
||||
"preview": "vite preview"
|
||||
},
|
||||
"dependencies": {
|
||||
"@react-three/drei": "^9.66.1",
|
||||
"@react-three/fiber": "^8.13.0",
|
||||
"@react-three/postprocessing": "^2.10.0",
|
||||
"axios": "^1.4.0",
|
||||
"babel-plugin": "^1.0.7",
|
||||
"glsl": "^0.0.1",
|
||||
"glsl-noise": "^0.0.0",
|
||||
"glslify": "^7.1.1",
|
||||
"leva": "^0.9.34",
|
||||
"react": "^18.2.0",
|
||||
"react-dom": "^18.2.0",
|
||||
"react-router": "^6.11.0",
|
||||
"react-router-dom": "^6.11.0",
|
||||
"three": "^0.152.2"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/react": "^18.0.28",
|
||||
"@types/react-dom": "^18.0.11",
|
||||
"@vitejs/plugin-react": "^4.0.0",
|
||||
"eslint": "^8.38.0",
|
||||
"eslint-plugin-react": "^7.32.2",
|
||||
"eslint-plugin-react-hooks": "^4.6.0",
|
||||
"eslint-plugin-react-refresh": "^0.3.4",
|
||||
"vite": "^4.3.2",
|
||||
"vite-plugin-glsl": "^1.1.2"
|
||||
}
|
||||
}
|
||||
11
ring.svg
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
<!-- Uploaded to: SVG Repo, www.svgrepo.com, Generator: SVG Repo Mixer Tools -->
|
||||
<svg fill="#ffffff" height="800px" width="800px" version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
viewBox="0 0 512 512" xml:space="preserve">
|
||||
<g>
|
||||
<g>
|
||||
<path d="M256,0C114.842,0,0,114.842,0,256s114.842,256,256,256s256-114.842,256-256S397.158,0,256,0z M256,486.4
|
||||
C128.751,486.4,25.6,383.249,25.6,256S128.751,25.6,256,25.6S486.4,128.751,486.4,256S383.249,486.4,256,486.4z"/>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 588 B |
13
src/App.css
Normal file
|
|
@ -0,0 +1,13 @@
|
|||
* {
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
html,
|
||||
body,
|
||||
#root,
|
||||
#canvas-container {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
7
src/App.jsx
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
import { createRoot } from "react-dom/client";
|
||||
import App from "./main";
|
||||
import "../src/App.css";
|
||||
|
||||
const container = document.getElementById("root");
|
||||
const root = createRoot(container);
|
||||
root.render(<App />);
|
||||
160
src/Scene1.jsx
Normal file
|
|
@ -0,0 +1,160 @@
|
|||
import { Canvas, extend, useFrame, useLoader } from "@react-three/fiber";
|
||||
import { shaderMaterial } from "@react-three/drei";
|
||||
import React, { useRef, Suspense } from "react";
|
||||
import * as THREE from "three";
|
||||
import glsl from "glslify";
|
||||
|
||||
const WaveShaderMaterial = shaderMaterial(
|
||||
//Uniform
|
||||
{
|
||||
uTime: 0,
|
||||
uColor: new THREE.Color(0.0, 0.0, 0.0),
|
||||
},
|
||||
//Vertex Shader
|
||||
glsl`
|
||||
precision mediump float;
|
||||
|
||||
uniform float uTime;
|
||||
|
||||
varying vec2 vUv;
|
||||
|
||||
vec3 mod289(vec3 x) {
|
||||
return x - floor(x * (1.0 / 289.0)) * 289.0;
|
||||
}
|
||||
|
||||
vec4 mod289(vec4 x) {
|
||||
return x - floor(x * (1.0 / 289.0)) * 289.0;
|
||||
}
|
||||
|
||||
vec4 permute(vec4 x) {
|
||||
return mod289(((x*34.0)+10.0)*x);
|
||||
}
|
||||
|
||||
vec4 taylorInvSqrt(vec4 r)
|
||||
{
|
||||
return 1.79284291400159 - 0.85373472095314 * r;
|
||||
}
|
||||
|
||||
float snoise(vec3 v)
|
||||
{
|
||||
const vec2 C = vec2(1.0/6.0, 1.0/3.0) ;
|
||||
const vec4 D = vec4(0.0, 0.5, 1.0, 2.0);
|
||||
|
||||
// First corner
|
||||
vec3 i = floor(v + dot(v, C.yyy) );
|
||||
vec3 x0 = v - i + dot(i, C.xxx) ;
|
||||
|
||||
// Other corners
|
||||
vec3 g = step(x0.yzx, x0.xyz);
|
||||
vec3 l = 1.0 - g;
|
||||
vec3 i1 = min( g.xyz, l.zxy );
|
||||
vec3 i2 = max( g.xyz, l.zxy );
|
||||
|
||||
// x0 = x0 - 0.0 + 0.0 * C.xxx;
|
||||
// x1 = x0 - i1 + 1.0 * C.xxx;
|
||||
// x2 = x0 - i2 + 2.0 * C.xxx;
|
||||
// x3 = x0 - 1.0 + 3.0 * C.xxx;
|
||||
vec3 x1 = x0 - i1 + C.xxx;
|
||||
vec3 x2 = x0 - i2 + C.yyy; // 2.0*C.x = 1/3 = C.y
|
||||
vec3 x3 = x0 - D.yyy; // -1.0+3.0*C.x = -0.5 = -D.y
|
||||
|
||||
// Permutations
|
||||
i = mod289(i);
|
||||
vec4 p = permute( permute( permute(
|
||||
i.z + vec4(0.0, i1.z, i2.z, 1.0 ))
|
||||
+ i.y + vec4(0.0, i1.y, i2.y, 1.0 ))
|
||||
+ i.x + vec4(0.0, i1.x, i2.x, 1.0 ));
|
||||
|
||||
// Gradients: 7x7 points over a square, mapped onto an octahedron.
|
||||
// The ring size 17*17 = 289 is close to a multiple of 49 (49*6 = 294)
|
||||
float n_ = 0.142857142857; // 1.0/7.0
|
||||
vec3 ns = n_ * D.wyz - D.xzx;
|
||||
|
||||
vec4 j = p - 49.0 * floor(p * ns.z * ns.z); // mod(p,7*7)
|
||||
|
||||
vec4 x_ = floor(j * ns.z);
|
||||
vec4 y_ = floor(j - 7.0 * x_ ); // mod(j,N)
|
||||
|
||||
vec4 x = x_ *ns.x + ns.yyyy;
|
||||
vec4 y = y_ *ns.x + ns.yyyy;
|
||||
vec4 h = 1.0 - abs(x) - abs(y);
|
||||
|
||||
vec4 b0 = vec4( x.xy, y.xy );
|
||||
vec4 b1 = vec4( x.zw, y.zw );
|
||||
|
||||
//vec4 s0 = vec4(lessThan(b0,0.0))*2.0 - 1.0;
|
||||
//vec4 s1 = vec4(lessThan(b1,0.0))*2.0 - 1.0;
|
||||
vec4 s0 = floor(b0)*2.0 + 1.0;
|
||||
vec4 s1 = floor(b1)*2.0 + 1.0;
|
||||
vec4 sh = -step(h, vec4(0.0));
|
||||
|
||||
vec4 a0 = b0.xzyw + s0.xzyw*sh.xxyy ;
|
||||
vec4 a1 = b1.xzyw + s1.xzyw*sh.zzww ;
|
||||
|
||||
vec3 p0 = vec3(a0.xy,h.x);
|
||||
vec3 p1 = vec3(a0.zw,h.y);
|
||||
vec3 p2 = vec3(a1.xy,h.z);
|
||||
vec3 p3 = vec3(a1.zw,h.w);
|
||||
|
||||
//Normalise gradients
|
||||
vec4 norm = taylorInvSqrt(vec4(dot(p0,p0), dot(p1,p1), dot(p2, p2), dot(p3,p3)));
|
||||
p0 *= norm.x;
|
||||
p1 *= norm.y;
|
||||
p2 *= norm.z;
|
||||
p3 *= norm.w;
|
||||
|
||||
// Mix final noise value
|
||||
vec4 m = max(0.5 - vec4(dot(x0,x0), dot(x1,x1), dot(x2,x2), dot(x3,x3)), 0.0);
|
||||
m = m * m;
|
||||
return 105.0 * dot( m*m, vec4( dot(p0,x0), dot(p1,x1),
|
||||
dot(p2,x2), dot(p3,x3) ) );
|
||||
}
|
||||
|
||||
void main(){
|
||||
vUv = uv;
|
||||
|
||||
vec3 pos = position;
|
||||
float noiseFreq = 0.25;
|
||||
float noiseAmp = 0.25;
|
||||
vec3 noisePos = vec3(pos.x * noiseFreq + uTime, pos.y, pos.z);
|
||||
pos.z += snoise(noisePos) * noiseAmp;
|
||||
gl_Position = projectionMatrix * modelViewMatrix * vec4(pos, 1.0);
|
||||
}`,
|
||||
//Fragment Shader
|
||||
glsl`
|
||||
precision mediump float;
|
||||
|
||||
uniform vec3 uColor;
|
||||
uniform float uTime;
|
||||
|
||||
varying vec2 vUv;
|
||||
|
||||
void main(){
|
||||
gl_FragColor = vec4(cos(vUv.x + uTime*2.0) * uColor, 1.0);
|
||||
}`
|
||||
);
|
||||
|
||||
extend({ WaveShaderMaterial });
|
||||
|
||||
const Wave = () => {
|
||||
const ref = useRef();
|
||||
useFrame(({ clock }) => (ref.current.uTime = clock.getElapsedTime()));
|
||||
return (
|
||||
<mesh>
|
||||
<planeGeometry args={[0.4, 0.6, 16, 16]} />
|
||||
<waveShaderMaterial uColor={"lightblue"} ref={ref} />
|
||||
</mesh>
|
||||
);
|
||||
};
|
||||
|
||||
const Scene = () => {
|
||||
return (
|
||||
<Canvas camera={{ fov: 10 }}>
|
||||
<Suspense fallback={null}>
|
||||
<Wave />
|
||||
</Suspense>
|
||||
</Canvas>
|
||||
);
|
||||
};
|
||||
|
||||
export default Scene;
|
||||
160
src/Scene2.jsx
Normal file
|
|
@ -0,0 +1,160 @@
|
|||
import { Canvas, extend, useFrame } from "@react-three/fiber";
|
||||
import { shaderMaterial } from "@react-three/drei";
|
||||
import React, { useRef, Suspense } from "react";
|
||||
import * as THREE from "three";
|
||||
import glsl from "glslify";
|
||||
|
||||
const WaveShaderMaterial = shaderMaterial(
|
||||
//Uniform
|
||||
{
|
||||
uTime: 0,
|
||||
uColor: new THREE.Color(0.0, 0.0, 0.0),
|
||||
},
|
||||
//Vertex Shader
|
||||
glsl`
|
||||
precision mediump float;
|
||||
|
||||
uniform float uTime;
|
||||
|
||||
varying vec2 vUv;
|
||||
|
||||
vec3 mod289(vec3 x) {
|
||||
return x - floor(x * (1.0 / 289.0)) * 289.0;
|
||||
}
|
||||
|
||||
vec4 mod289(vec4 x) {
|
||||
return x - floor(x * (1.0 / 289.0)) * 289.0;
|
||||
}
|
||||
|
||||
vec4 permute(vec4 x) {
|
||||
return mod289(((x*34.0)+10.0)*x);
|
||||
}
|
||||
|
||||
vec4 taylorInvSqrt(vec4 r)
|
||||
{
|
||||
return 1.79284291400159 - 0.85373472095314 * r;
|
||||
}
|
||||
|
||||
float snoise(vec3 v)
|
||||
{
|
||||
const vec2 C = vec2(1.0/6.0, 1.0/3.0) ;
|
||||
const vec4 D = vec4(0.0, 0.5, 1.0, 2.0);
|
||||
|
||||
// First corner
|
||||
vec3 i = floor(v + dot(v, C.yyy) );
|
||||
vec3 x0 = v - i + dot(i, C.xxx) ;
|
||||
|
||||
// Other corners
|
||||
vec3 g = step(x0.yzx, x0.xyz);
|
||||
vec3 l = 1.0 - g;
|
||||
vec3 i1 = min( g.xyz, l.zxy );
|
||||
vec3 i2 = max( g.xyz, l.zxy );
|
||||
|
||||
// x0 = x0 - 0.0 + 0.0 * C.xxx;
|
||||
// x1 = x0 - i1 + 1.0 * C.xxx;
|
||||
// x2 = x0 - i2 + 2.0 * C.xxx;
|
||||
// x3 = x0 - 1.0 + 3.0 * C.xxx;
|
||||
vec3 x1 = x0 - i1 + C.xxx;
|
||||
vec3 x2 = x0 - i2 + C.yyy; // 2.0*C.x = 1/3 = C.y
|
||||
vec3 x3 = x0 - D.yyy; // -1.0+3.0*C.x = -0.5 = -D.y
|
||||
|
||||
// Permutations
|
||||
i = mod289(i);
|
||||
vec4 p = permute( permute( permute(
|
||||
i.z + vec4(0.0, i1.z, i2.z, 1.0 ))
|
||||
+ i.y + vec4(0.0, i1.y, i2.y, 1.0 ))
|
||||
+ i.x + vec4(0.0, i1.x, i2.x, 1.0 ));
|
||||
|
||||
// Gradients: 7x7 points over a square, mapped onto an octahedron.
|
||||
// The ring size 17*17 = 289 is close to a multiple of 49 (49*6 = 294)
|
||||
float n_ = 0.142857142857; // 1.0/7.0
|
||||
vec3 ns = n_ * D.wyz - D.xzx;
|
||||
|
||||
vec4 j = p - 49.0 * floor(p * ns.z * ns.z); // mod(p,7*7)
|
||||
|
||||
vec4 x_ = floor(j * ns.z);
|
||||
vec4 y_ = floor(j - 7.0 * x_ ); // mod(j,N)
|
||||
|
||||
vec4 x = x_ *ns.x + ns.yyyy;
|
||||
vec4 y = y_ *ns.x + ns.yyyy;
|
||||
vec4 h = 1.0 - abs(x) - abs(y);
|
||||
|
||||
vec4 b0 = vec4( x.xy, y.xy );
|
||||
vec4 b1 = vec4( x.zw, y.zw );
|
||||
|
||||
//vec4 s0 = vec4(lessThan(b0,0.0))*2.0 - 1.0;
|
||||
//vec4 s1 = vec4(lessThan(b1,0.0))*2.0 - 1.0;
|
||||
vec4 s0 = floor(b0)*2.0 + 1.0;
|
||||
vec4 s1 = floor(b1)*2.0 + 1.0;
|
||||
vec4 sh = -step(h, vec4(0.0));
|
||||
|
||||
vec4 a0 = b0.xzyw + s0.xzyw*sh.xxyy ;
|
||||
vec4 a1 = b1.xzyw + s1.xzyw*sh.zzww ;
|
||||
|
||||
vec3 p0 = vec3(a0.xy,h.x);
|
||||
vec3 p1 = vec3(a0.zw,h.y);
|
||||
vec3 p2 = vec3(a1.xy,h.z);
|
||||
vec3 p3 = vec3(a1.zw,h.w);
|
||||
|
||||
//Normalise gradients
|
||||
vec4 norm = taylorInvSqrt(vec4(dot(p0,p0), dot(p1,p1), dot(p2, p2), dot(p3,p3)));
|
||||
p0 *= norm.x;
|
||||
p1 *= norm.y;
|
||||
p2 *= norm.z;
|
||||
p3 *= norm.w;
|
||||
|
||||
// Mix final noise value
|
||||
vec4 m = max(0.5 - vec4(dot(x0,x0), dot(x1,x1), dot(x2,x2), dot(x3,x3)), 0.0);
|
||||
m = m * m;
|
||||
return 105.0 * dot( m*m, vec4( dot(p0,x0), dot(p1,x1),
|
||||
dot(p2,x2), dot(p3,x3) ) );
|
||||
}
|
||||
|
||||
void main(){
|
||||
vUv = uv;
|
||||
|
||||
vec3 pos = position;
|
||||
float noiseFreq = 0.25;
|
||||
float noiseAmp = 0.25;
|
||||
vec3 noisePos = vec3(pos.x * noiseFreq + uTime, pos.y, pos.z);
|
||||
pos.z += snoise(noisePos) * noiseAmp;
|
||||
gl_Position = projectionMatrix * modelViewMatrix * vec4(pos, 1.0);
|
||||
}`,
|
||||
//Fragment Shader
|
||||
glsl`
|
||||
precision mediump float;
|
||||
|
||||
uniform vec3 uColor;
|
||||
uniform float uTime;
|
||||
|
||||
varying vec2 vUv;
|
||||
|
||||
void main(){
|
||||
gl_FragColor = vec4(cos(vUv.x + uTime*2.0) * uColor, 1.0);
|
||||
}`
|
||||
);
|
||||
|
||||
extend({ WaveShaderMaterial });
|
||||
|
||||
const Wave = () => {
|
||||
const ref = useRef();
|
||||
useFrame(({ clock }) => (ref.current.uTime = clock.getElapsedTime()));
|
||||
return (
|
||||
<mesh>
|
||||
<planeGeometry args={[0.4, 0.6, 16, 16]} />
|
||||
<waveShaderMaterial uColor={"red"} ref={ref} />
|
||||
</mesh>
|
||||
);
|
||||
};
|
||||
|
||||
const Scene1 = () => {
|
||||
return (
|
||||
<Canvas camera={{ fov: 10 }}>
|
||||
<Suspense fallback={null}>
|
||||
<Wave />
|
||||
</Suspense>
|
||||
</Canvas>
|
||||
);
|
||||
};
|
||||
|
||||
export default Scene1;
|
||||
127
src/Scene3.jsx
Normal file
|
|
@ -0,0 +1,127 @@
|
|||
import { Canvas, useFrame, useThree } from "@react-three/fiber";
|
||||
import { OrbitControls, PerspectiveCamera } from "@react-three/drei";
|
||||
import React, {
|
||||
Suspense,
|
||||
useState,
|
||||
useEffect,
|
||||
useRef,
|
||||
createContext,
|
||||
useContext,
|
||||
forwardRef,
|
||||
memo,
|
||||
useMemo,
|
||||
} from "react";
|
||||
import { Earth } from "./earth.jsx";
|
||||
import { Mars } from "./mars.jsx";
|
||||
import { Jupiter } from "./jupiter.jsx";
|
||||
import { Saturn } from "./saturn.jsx";
|
||||
import { Mercury } from "./mercury.jsx";
|
||||
import { Venus } from "./venus.jsx";
|
||||
import { Neptune } from "./neptune.jsx";
|
||||
import { Uranus } from "./uranus.jsx";
|
||||
import { Sun } from "./sun.jsx";
|
||||
import * as THREE from "three";
|
||||
import { PlanetInfo } from "./planetInfo.jsx";
|
||||
import { Skybox } from "./skybox.jsx";
|
||||
import {
|
||||
Selection,
|
||||
Select,
|
||||
EffectComposer,
|
||||
Outline,
|
||||
} from "@react-three/postprocessing";
|
||||
|
||||
export const MyContext = createContext();
|
||||
export const OtherContext = createContext();
|
||||
|
||||
import { SharedPlanetState } from "./SharedPlanetState.jsx";
|
||||
|
||||
const SolarSystemScene = () => {
|
||||
const [data, setData] = useState(null);
|
||||
const [vis, setVis] = useState("hidden");
|
||||
const controls = useRef();
|
||||
const planetinfo = useRef();
|
||||
let customData = useRef({});
|
||||
|
||||
useEffect(() => {
|
||||
const fetchData = async () => {
|
||||
let res = await fetch(
|
||||
"http://127.0.0.1:8000/duration?date=2023-08-06T21:53" //example and simple data
|
||||
);
|
||||
let response = await res.json();
|
||||
setData(response); // parse json
|
||||
//console.log(response);
|
||||
};
|
||||
fetchData();
|
||||
}, []);
|
||||
|
||||
function toggleVisibility() {
|
||||
console.log(vis);
|
||||
if (vis === "hidden") {
|
||||
setVis("visible");
|
||||
console.log("what");
|
||||
} else if (vis === "visible") {
|
||||
setVis("hidden");
|
||||
console.log("asdasd");
|
||||
}
|
||||
}
|
||||
|
||||
function handleChange(event) {
|
||||
console.log(event.target.value);
|
||||
customData.current.changeEarthSpeed(event.target.value);
|
||||
customData.current.changeMarsSpeed(event.target.value);
|
||||
customData.current.changeVenusSpeed(event.target.value);
|
||||
customData.current.changeSaturnSpeed(event.target.value);
|
||||
customData.current.changeUranusSpeed(event.target.value);
|
||||
customData.current.changeJupiterSpeed(event.target.value);
|
||||
customData.current.changeMercurySpeed(event.target.value);
|
||||
customData.current.changeNeptuneSpeed(event.target.value);
|
||||
}
|
||||
|
||||
if (data)
|
||||
return (
|
||||
<>
|
||||
<div className="slidecontainer">
|
||||
<input
|
||||
type="range"
|
||||
min="10"
|
||||
max="360"
|
||||
className="slider"
|
||||
onChange={handleChange}
|
||||
id="myRange"
|
||||
/>
|
||||
</div>
|
||||
<MyContext.Provider value={{ controls, toggleVisibility, customData }}>
|
||||
<PlanetInfo ref={planetinfo} visi={vis} />
|
||||
<Suspense fallback={null}>
|
||||
<Canvas
|
||||
camera={{
|
||||
fov: 75,
|
||||
near: 0.1,
|
||||
far: 10000000,
|
||||
position: [0, 100, 200],
|
||||
}}
|
||||
>
|
||||
<Skybox />
|
||||
<ambientLight intensity={0.5} />
|
||||
|
||||
<Earth positions={data["399"]} onClick={(e) => console.log(e)} />
|
||||
<Mars positions={data["499"]} />
|
||||
<Jupiter positions={data["599"]} />
|
||||
<Saturn positions={data["699"]} />
|
||||
<Mercury positions={data["199"]} />
|
||||
<Venus positions={data["299"]} />
|
||||
<Neptune positions={data["899"]} />
|
||||
<Uranus positions={data["799"]} />
|
||||
<Sun />
|
||||
|
||||
<OrbitControls ref={controls} maxZoom={10} />
|
||||
</Canvas>
|
||||
</Suspense>
|
||||
</MyContext.Provider>
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
const Smemo = memo(SolarSystemScene, true);
|
||||
|
||||
export default Smemo;
|
||||
96
src/SharedPlanetState.jsx
Normal file
|
|
@ -0,0 +1,96 @@
|
|||
import { Canvas, useFrame, useThree } from "@react-three/fiber";
|
||||
import { OrbitControls, PerspectiveCamera } from "@react-three/drei";
|
||||
import React, {
|
||||
Suspense,
|
||||
useState,
|
||||
useEffect,
|
||||
useRef,
|
||||
createContext,
|
||||
useContext,
|
||||
forwardRef,
|
||||
memo,
|
||||
useMemo,
|
||||
} from "react";
|
||||
import { Earth } from "./earth.jsx";
|
||||
import { Mars } from "./mars.jsx";
|
||||
import { Jupiter } from "./jupiter.jsx";
|
||||
import { Saturn } from "./saturn.jsx";
|
||||
import { Mercury } from "./mercury.jsx";
|
||||
import { Venus } from "./venus.jsx";
|
||||
import { Neptune } from "./neptune.jsx";
|
||||
import { Uranus } from "./uranus.jsx";
|
||||
import { Sun } from "./sun.jsx";
|
||||
import * as THREE from "three";
|
||||
import { PlanetInfo } from "./planetInfo.jsx";
|
||||
import { Skybox } from "./skybox.jsx";
|
||||
import {
|
||||
Selection,
|
||||
Select,
|
||||
EffectComposer,
|
||||
Outline,
|
||||
} from "@react-three/postprocessing";
|
||||
|
||||
export const SharedPlanetState = () => {
|
||||
const [data, setData] = useState(null);
|
||||
const [vis, setVis] = useState("hidden");
|
||||
const controls = useRef();
|
||||
const planetinfo = useRef();
|
||||
let customData = useRef({});
|
||||
|
||||
function toggleVisibility() {
|
||||
console.log(vis);
|
||||
if (vis === "hidden") {
|
||||
setVis("visible");
|
||||
console.log("what");
|
||||
} else if (vis === "visible") {
|
||||
setVis("hidden");
|
||||
console.log("asdasd");
|
||||
}
|
||||
}
|
||||
|
||||
function handleChange(event) {
|
||||
console.log(event.target.value);
|
||||
customData.current.changeEarthSpeed(event.target.value);
|
||||
customData.current.changeMarsSpeed(event.target.value);
|
||||
customData.current.changeVenusSpeed(event.target.value);
|
||||
customData.current.changeSaturnSpeed(event.target.value);
|
||||
customData.current.changeUranusSpeed(event.target.value);
|
||||
customData.current.changeJupiterSpeed(event.target.value);
|
||||
customData.current.changeMercurySpeed(event.target.value);
|
||||
customData.current.changeNeptuneSpeed(event.target.value);
|
||||
}
|
||||
|
||||
const [speed, setSpeed] = useState();
|
||||
|
||||
const updateSpeed = (newSpeed) => setSpeed(newSpeed);
|
||||
return (
|
||||
<>
|
||||
<PlanetInfo ref={planetinfo} visi={vis} />
|
||||
<Suspense fallback={null}>
|
||||
<Canvas
|
||||
camera={{
|
||||
fov: 75,
|
||||
near: 0.1,
|
||||
far: 10000000,
|
||||
position: [0, 100, 200],
|
||||
}}
|
||||
>
|
||||
<Skybox />
|
||||
<ambientLight intensity={0.5} />
|
||||
|
||||
<Earth positions={data["399"]} onClick={(e) => console.log(e)} />
|
||||
<Mars positions={data["499"]} />
|
||||
<Jupiter positions={data["599"]} />
|
||||
<Saturn positions={data["699"]} />
|
||||
<Mercury positions={data["199"]} />
|
||||
<Venus positions={data["299"]} />
|
||||
<Neptune positions={data["899"]} />
|
||||
<Uranus positions={data["799"]} />
|
||||
<Sun />
|
||||
|
||||
<OrbitControls ref={controls} maxZoom={10} />
|
||||
</Canvas>
|
||||
</Suspense>
|
||||
</>
|
||||
);
|
||||
};
|
||||
61
src/TestScene.jsx
Normal file
|
|
@ -0,0 +1,61 @@
|
|||
import { Canvas, useThree } from "@react-three/fiber";
|
||||
import { OrbitControls } from "@react-three/drei";
|
||||
import React, { Suspense, useState, useEffect, useRef } from "react";
|
||||
import { Earth } from "./earth.jsx";
|
||||
import { Mars } from "./mars.jsx";
|
||||
import { Jupiter } from "./jupiter.jsx";
|
||||
import { Saturn } from "./saturn.jsx";
|
||||
import * as THREE from "three";
|
||||
import {
|
||||
Selection,
|
||||
Select,
|
||||
EffectComposer,
|
||||
Outline,
|
||||
} from "@react-three/postprocessing";
|
||||
|
||||
const TestScene = () => {
|
||||
const [data, setData] = useState(null);
|
||||
useEffect(() => {
|
||||
console.log("useeffect called");
|
||||
const fetchData = async () => {
|
||||
let res = await fetch(
|
||||
"http://127.0.0.1:8000/duration" //example and simple data
|
||||
);
|
||||
let response = await res.json();
|
||||
setData(response); // parse json
|
||||
console.log(response);
|
||||
};
|
||||
fetchData();
|
||||
}, []);
|
||||
|
||||
const Skybox = () => {
|
||||
const { scene } = useThree();
|
||||
const loader = new THREE.CubeTextureLoader();
|
||||
const box = loader.load([
|
||||
"../img/skybox/front.png",
|
||||
"../img/skybox/back.png",
|
||||
"../img/skybox/top.png",
|
||||
"../img/skybox/bottom.png",
|
||||
"../img/skybox/left.png",
|
||||
"../img/skybox/right.png",
|
||||
]);
|
||||
scene.background = box;
|
||||
return null;
|
||||
};
|
||||
|
||||
if (data)
|
||||
return (
|
||||
<>
|
||||
<Canvas camera={{ position: [0, 0, 15] }}>
|
||||
<ambientLight intensity={0.1} />
|
||||
<pointLight position={[15, 15, 15]} intensity={0.5} />
|
||||
<Suspense fallback={null}>
|
||||
<Earth parentToChild={data["399"]} />
|
||||
</Suspense>
|
||||
<OrbitControls />
|
||||
</Canvas>
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
export default TestScene;
|
||||
178
src/earth.jsx
Normal file
|
|
@ -0,0 +1,178 @@
|
|||
import {
|
||||
Canvas,
|
||||
extend,
|
||||
useFrame,
|
||||
useLoader,
|
||||
useThree,
|
||||
} from "@react-three/fiber";
|
||||
import {
|
||||
shaderMaterial,
|
||||
OrbitControls,
|
||||
Line,
|
||||
Html,
|
||||
Text,
|
||||
} from "@react-three/drei";
|
||||
import React, {
|
||||
useRef,
|
||||
Suspense,
|
||||
useLayoutEffect,
|
||||
useState,
|
||||
useEffect,
|
||||
useContext,
|
||||
} from "react";
|
||||
import * as THREE from "three";
|
||||
import glsl from "glslify";
|
||||
import { TextureLoader } from "three/src/loaders/TextureLoader";
|
||||
import {
|
||||
Selection,
|
||||
Select,
|
||||
EffectComposer,
|
||||
Outline,
|
||||
Scanline,
|
||||
} from "@react-three/postprocessing";
|
||||
import "./styles.css";
|
||||
|
||||
import { PlanetOverlay } from "./planetOverlay";
|
||||
import { PlanetInfo } from "./planetInfo";
|
||||
import { PlanetPath } from "./path";
|
||||
import { MyContext } from "./Scene3";
|
||||
|
||||
export const Earth = ({ positions }) => {
|
||||
let distanceScaleFactor = 1000000;
|
||||
const [poss, setPos] = useState([]);
|
||||
const [lineposs, setLinePos] = useState([]);
|
||||
const [getAgain, setGetAgain] = useState(false);
|
||||
const [speed, setSpeed] = useState(60);
|
||||
const line = useRef();
|
||||
const clouds = useRef("clouds");
|
||||
const earth = useRef();
|
||||
const group = useRef();
|
||||
const firstRef = useRef(true);
|
||||
let linePoss = [];
|
||||
const { customData } = useContext(MyContext);
|
||||
|
||||
useLayoutEffect(() => {
|
||||
group.current.userData.counter = 0;
|
||||
group.current.userData.name = "Earth";
|
||||
group.current.userData.nearOvOp = 60;
|
||||
group.current.userData.scolor = "lightgreen";
|
||||
}, []);
|
||||
|
||||
function datas() {
|
||||
return group;
|
||||
}
|
||||
|
||||
let currLinePoss = [];
|
||||
|
||||
useFrame(() => {
|
||||
if (poss.length % 1000 == 0) {
|
||||
setPos(poss.slice(0, 500));
|
||||
}
|
||||
let date;
|
||||
if (firstRef.current) {
|
||||
date = new Date(Date.now());
|
||||
date.setMilliseconds(0);
|
||||
date.setSeconds(0);
|
||||
}
|
||||
//console.log(poss.length);
|
||||
//console.log(group.current.userData.counter);
|
||||
if (group.current.userData.counter % 250 == 0 || getAgain) {
|
||||
if (!firstRef.current)
|
||||
date = new Date(poss[poss.length - 1].date).toUTCString();
|
||||
const fetchData = async () => {
|
||||
let res = await fetch(
|
||||
`http://127.0.0.1:8000/duration/earth?date=${date}&speed=${speed}` //example and simple data
|
||||
);
|
||||
let response = await res.json();
|
||||
|
||||
setPos(poss.concat(response)); // parse json
|
||||
firstRef.current = false;
|
||||
setGetAgain(false);
|
||||
//console.log(`psss : ${poss.length}`);
|
||||
};
|
||||
fetchData();
|
||||
}
|
||||
clouds.current.rotation.y += 0.00025;
|
||||
earth.current.rotation.y += 0.00015;
|
||||
if (true && group.current.userData.counter < poss.length) {
|
||||
group.current.position.set(
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.x / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.y / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.z / distanceScaleFactor
|
||||
)
|
||||
);
|
||||
//console.log(group.current.userData.counter);
|
||||
group.current.userData.counter++;
|
||||
}
|
||||
}, []);
|
||||
|
||||
const changeSpeed = (newSpeed) => {
|
||||
setPos(poss.slice(0, group.current.userData.counter + 10));
|
||||
setGetAgain(true);
|
||||
console.log(poss);
|
||||
setSpeed(newSpeed);
|
||||
};
|
||||
|
||||
customData.current["changeEarthSpeed"] = changeSpeed;
|
||||
|
||||
const col = useLoader(TextureLoader, "../img/earth/6k_earth_daymap.jpg");
|
||||
const bump = useLoader(TextureLoader, "../img/earth/earth_bump_1k.jpg");
|
||||
const spec = useLoader(
|
||||
TextureLoader,
|
||||
"../img/earth/6k_earth_specular_map.jpg"
|
||||
);
|
||||
const norm = useLoader(TextureLoader, "../img/earth/6k_earth_normal_map.jpg");
|
||||
const cloudMap = useLoader(TextureLoader, "../img/earth/6k_earth_clouds.jpg");
|
||||
const axisPoints = [
|
||||
new THREE.Vector3(0, 6371.0 / 6000 + 0.5, 0),
|
||||
new THREE.Vector3(0, -(6371.0 / 6000 + 0.5), 0),
|
||||
];
|
||||
useLayoutEffect(() => {
|
||||
line.current.geometry.setFromPoints(axisPoints);
|
||||
});
|
||||
return (
|
||||
<>
|
||||
<PlanetPath
|
||||
positions={poss.slice(0, 1000)}
|
||||
linePos={poss}
|
||||
planet={group}
|
||||
lineAt={group.current ? group.current.userData.counter : 0}
|
||||
color={"lightgreen"}
|
||||
datas={datas}
|
||||
lineLength={20}
|
||||
/>
|
||||
<group ref={group}>
|
||||
<PlanetOverlay planet={group} />
|
||||
<mesh ref={earth}>
|
||||
<sphereGeometry args={[6371.0 / 6000, 50, 50]} />
|
||||
<meshPhongMaterial
|
||||
map={col}
|
||||
bumpMap={bump}
|
||||
specularMap={spec}
|
||||
normalMap={norm}
|
||||
bumpScale={0.2}
|
||||
shininess={0.5}
|
||||
/>
|
||||
</mesh>
|
||||
<mesh ref={clouds}>
|
||||
<sphereGeometry args={[6371.0 / 6000 + 0.01, 50, 50]} />
|
||||
<meshPhongMaterial map={cloudMap} transparent={true} opacity={0.5} />
|
||||
</mesh>
|
||||
<line ref={line}>
|
||||
<bufferGeometry />
|
||||
<lineBasicMaterial
|
||||
color={"hotpink"}
|
||||
transparent={true}
|
||||
opacity={0.5}
|
||||
linewidth={2}
|
||||
/>
|
||||
</line>
|
||||
</group>
|
||||
</>
|
||||
);
|
||||
};
|
||||
110
src/jupiter.jsx
Normal file
|
|
@ -0,0 +1,110 @@
|
|||
import { Canvas, extend, useFrame, useLoader } from "@react-three/fiber";
|
||||
import { shaderMaterial, OrbitControls, Line } from "@react-three/drei";
|
||||
import React, {
|
||||
useRef,
|
||||
Suspense,
|
||||
useLayoutEffect,
|
||||
useEffect,
|
||||
useState,
|
||||
useContext,
|
||||
} from "react";
|
||||
import * as THREE from "three";
|
||||
import glsl from "glslify";
|
||||
import { TextureLoader } from "three/src/loaders/TextureLoader";
|
||||
import { PlanetOverlay } from "./planetOverlay";
|
||||
import { PlanetPath } from "./path";
|
||||
import { MyContext } from "./Scene3";
|
||||
|
||||
export const Jupiter = ({ positions }) => {
|
||||
const [poss, setPos] = useState([]);
|
||||
const [lineposs, setLinePos] = useState([]);
|
||||
const [getAgain, setGetAgain] = useState(false);
|
||||
const [speed, setSpeed] = useState(60);
|
||||
const jupiter = useRef("jupiter");
|
||||
const group = useRef();
|
||||
const col = useLoader(TextureLoader, "../img/jupiter/jupiter2_4k.jpg");
|
||||
|
||||
let distanceScaleFactor = 1000000;
|
||||
|
||||
const firstRef = useRef(true);
|
||||
let linePoss = [];
|
||||
const { customData } = useContext(MyContext);
|
||||
|
||||
useEffect(() => {
|
||||
group.current.userData.counter = 0;
|
||||
group.current.userData.name = "Jupiter";
|
||||
group.current.userData.nearOvOp = 800;
|
||||
group.current.userData.scolor = "yellow";
|
||||
});
|
||||
|
||||
useFrame(() => {
|
||||
if (poss.length % 1000 == 0) {
|
||||
setPos(poss.slice(0, 500));
|
||||
}
|
||||
let date;
|
||||
if (firstRef.current) {
|
||||
date = new Date(Date.now());
|
||||
date.setMilliseconds(0);
|
||||
date.setSeconds(0);
|
||||
}
|
||||
//console.log(poss.length);
|
||||
//console.log(group.current.userData.counter);
|
||||
if (group.current.userData.counter % 250 == 0 || getAgain) {
|
||||
if (!firstRef.current)
|
||||
date = new Date(poss[poss.length - 1].date).toUTCString();
|
||||
const fetchData = async () => {
|
||||
let res = await fetch(
|
||||
`http://127.0.0.1:8000/duration/jupiter?date=${date}&speed=${speed}` //example and simple data
|
||||
);
|
||||
let response = await res.json();
|
||||
|
||||
setPos(poss.concat(response)); // parse json
|
||||
firstRef.current = false;
|
||||
setGetAgain(false);
|
||||
//console.log(`psss : ${poss.length}`);
|
||||
};
|
||||
fetchData();
|
||||
}
|
||||
if (true && group.current.userData.counter < poss.length) {
|
||||
group.current.position.set(
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.x / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.y / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.z / distanceScaleFactor
|
||||
)
|
||||
);
|
||||
//console.log(group.current.userData.counter);
|
||||
group.current.userData.counter++;
|
||||
}
|
||||
}, []);
|
||||
|
||||
const changeSpeed = (newSpeed) => {
|
||||
setPos(poss.slice(0, group.current.userData.counter + 10));
|
||||
setGetAgain(true);
|
||||
console.log(poss);
|
||||
setSpeed(newSpeed);
|
||||
};
|
||||
|
||||
customData.current["changeJupiterSpeed"] = changeSpeed;
|
||||
return (
|
||||
<>
|
||||
<PlanetPath
|
||||
linePos={poss}
|
||||
planet={group}
|
||||
color={"yellow"}
|
||||
lineLength={20}
|
||||
/>
|
||||
<group ref={group}>
|
||||
<PlanetOverlay planet={group} />
|
||||
<mesh>
|
||||
<sphereGeometry args={[69911 / 6000, 50, 50]} />
|
||||
<meshPhongMaterial map={col} />
|
||||
</mesh>
|
||||
</group>
|
||||
</>
|
||||
);
|
||||
};
|
||||
24
src/main.jsx
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
import { BrowserRouter, Routes, Route } from "react-router-dom";
|
||||
import Scene from "./Scene1";
|
||||
import Scene1 from "./Scene2";
|
||||
import SolarSystemScene from "./Scene3";
|
||||
import Smemo from "./Scene3";
|
||||
import React, { useEffect, useReducer, useState, useRef } from "react";
|
||||
import TestScene from "./TestScene";
|
||||
import SunScene from "./sunscene";
|
||||
|
||||
const App = () => {
|
||||
return (
|
||||
<BrowserRouter>
|
||||
<Routes>
|
||||
<Route path="/" element={<Scene />} />
|
||||
<Route path="next" element={<Scene1 />} />
|
||||
<Route path="solarsystem" element={<Smemo />} />
|
||||
<Route path="test" element={<TestScene />} />
|
||||
<Route path="sun" element={<SunScene />} />
|
||||
</Routes>
|
||||
</BrowserRouter>
|
||||
);
|
||||
};
|
||||
|
||||
export default App;
|
||||
112
src/mars.jsx
Normal file
|
|
@ -0,0 +1,112 @@
|
|||
import { Canvas, extend, useFrame, useLoader } from "@react-three/fiber";
|
||||
import { shaderMaterial, OrbitControls, Line } from "@react-three/drei";
|
||||
import React, {
|
||||
useRef,
|
||||
Suspense,
|
||||
useLayoutEffect,
|
||||
useState,
|
||||
useContext,
|
||||
} from "react";
|
||||
import * as THREE from "three";
|
||||
import { MyContext } from "./Scene3";
|
||||
import glsl from "glslify";
|
||||
import { TextureLoader } from "three/src/loaders/TextureLoader";
|
||||
import { PlanetOverlay } from "./planetOverlay";
|
||||
import { PlanetPath } from "./path";
|
||||
|
||||
export const Mars = ({ positions }) => {
|
||||
const mars = useRef("mars");
|
||||
const group = useRef("group");
|
||||
const [poss, setPos] = useState([]);
|
||||
const [getAgain, setGetAgain] = useState(false);
|
||||
const [speed, setSpeed] = useState(60);
|
||||
const firstRef = useRef(true);
|
||||
const col = useLoader(TextureLoader, "../img/mars/mars_1k_color.jpg");
|
||||
const bump = useLoader(TextureLoader, "../img/mars/mars_1k_topo.jpg");
|
||||
const norm = useLoader(TextureLoader, "../img/mars/mars_1k_normal.jpg");
|
||||
let distanceScaleFactor = 1000000;
|
||||
const { customData } = useContext(MyContext);
|
||||
|
||||
useLayoutEffect(() => {
|
||||
group.current.userData.counter = 0;
|
||||
group.current.userData.name = "Mars";
|
||||
group.current.userData.nearOvOp = 40;
|
||||
group.current.userData.scolor = "orange";
|
||||
}, []);
|
||||
|
||||
useFrame(() => {
|
||||
if (poss.length % 1000 == 0) {
|
||||
setPos(poss.slice(0, 500));
|
||||
}
|
||||
let date;
|
||||
if (firstRef.current) {
|
||||
date = new Date(Date.now());
|
||||
date.setMilliseconds(0);
|
||||
date.setSeconds(0);
|
||||
}
|
||||
//console.log(poss.length);
|
||||
//console.log(group.current.userData.counter);
|
||||
if (group.current.userData.counter % 250 == 0 || getAgain) {
|
||||
if (!firstRef.current)
|
||||
date = new Date(poss[poss.length - 1].date).toUTCString();
|
||||
const fetchData = async () => {
|
||||
let res = await fetch(
|
||||
`http://127.0.0.1:8000/duration/mars?date=${date}&speed=${speed}` //example and simple data
|
||||
);
|
||||
let response = await res.json();
|
||||
|
||||
setPos(poss.concat(response)); // parse json
|
||||
firstRef.current = false;
|
||||
setGetAgain(false);
|
||||
//console.log(`psss : ${poss.length}`);
|
||||
};
|
||||
fetchData();
|
||||
}
|
||||
if (true && group.current.userData.counter < poss.length) {
|
||||
group.current.position.set(
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.x / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.y / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.z / distanceScaleFactor
|
||||
)
|
||||
);
|
||||
//console.log(group.current.userData.counter);
|
||||
group.current.userData.counter++;
|
||||
}
|
||||
}, []);
|
||||
|
||||
const changeSpeed = (newSpeed) => {
|
||||
setPos(poss.slice(0, group.current.userData.counter + 10));
|
||||
setGetAgain(true);
|
||||
console.log(poss);
|
||||
setSpeed(newSpeed);
|
||||
};
|
||||
|
||||
customData.current["changeMarsSpeed"] = changeSpeed;
|
||||
return (
|
||||
<>
|
||||
<PlanetPath
|
||||
positions={positions}
|
||||
color={"orange"}
|
||||
linePos={poss}
|
||||
lineLength={50}
|
||||
/>
|
||||
<group ref={group}>
|
||||
<PlanetOverlay planet={group} />
|
||||
<mesh ref={mars}>
|
||||
<sphereGeometry args={[3389.5 / 6000, 50, 50]} />
|
||||
<meshPhongMaterial
|
||||
map={col}
|
||||
bumpMap={bump}
|
||||
normalMap={norm}
|
||||
bumpScale={0.3}
|
||||
/>
|
||||
</mesh>
|
||||
</group>
|
||||
</>
|
||||
);
|
||||
};
|
||||
132
src/mercury.jsx
Normal file
|
|
@ -0,0 +1,132 @@
|
|||
import {
|
||||
Canvas,
|
||||
extend,
|
||||
useFrame,
|
||||
useLoader,
|
||||
useThree,
|
||||
} from "@react-three/fiber";
|
||||
import {
|
||||
shaderMaterial,
|
||||
OrbitControls,
|
||||
Line,
|
||||
Html,
|
||||
Text,
|
||||
} from "@react-three/drei";
|
||||
import React, {
|
||||
useRef,
|
||||
Suspense,
|
||||
useLayoutEffect,
|
||||
useState,
|
||||
useEffect,
|
||||
useContext,
|
||||
} from "react";
|
||||
import * as THREE from "three";
|
||||
import glsl from "glslify";
|
||||
import { TextureLoader } from "three/src/loaders/TextureLoader";
|
||||
import {
|
||||
Selection,
|
||||
Select,
|
||||
EffectComposer,
|
||||
Outline,
|
||||
Scanline,
|
||||
} from "@react-three/postprocessing";
|
||||
import "./styles.css";
|
||||
|
||||
import { PlanetOverlay } from "./planetOverlay";
|
||||
import { PlanetPath } from "./path";
|
||||
import { MyContext } from "./Scene3";
|
||||
|
||||
export const Mercury = ({ positions }) => {
|
||||
const [poss, setPos] = useState([]);
|
||||
const [lineposs, setLinePos] = useState([]);
|
||||
const [getAgain, setGetAgain] = useState(false);
|
||||
const [speed, setSpeed] = useState(60);
|
||||
let distanceScaleFactor = 1000000;
|
||||
const mercury = useRef();
|
||||
const group = useRef();
|
||||
|
||||
const firstRef = useRef(true);
|
||||
let linePoss = [];
|
||||
const { customData } = useContext(MyContext);
|
||||
|
||||
useLayoutEffect(() => {
|
||||
group.current.userData.counter = 0;
|
||||
group.current.userData.name = "Mercury";
|
||||
group.current.userData.nearOvOp = 20;
|
||||
group.current.userData.scolor = "#a34f5f";
|
||||
}, []);
|
||||
|
||||
useFrame(() => {
|
||||
if (poss.length % 1000 == 0) {
|
||||
setPos(poss.slice(0, 500));
|
||||
}
|
||||
let date;
|
||||
if (firstRef.current) {
|
||||
date = new Date(Date.now());
|
||||
date.setMilliseconds(0);
|
||||
date.setSeconds(0);
|
||||
}
|
||||
//console.log(poss.length);
|
||||
//console.log(group.current.userData.counter);
|
||||
if (group.current.userData.counter % 250 == 0 || getAgain) {
|
||||
if (!firstRef.current)
|
||||
date = new Date(poss[poss.length - 1].date).toUTCString();
|
||||
const fetchData = async () => {
|
||||
let res = await fetch(
|
||||
`http://127.0.0.1:8000/duration/mercury?date=${date}&speed=${speed}` //example and simple data
|
||||
);
|
||||
let response = await res.json();
|
||||
|
||||
setPos(poss.concat(response)); // parse json
|
||||
firstRef.current = false;
|
||||
setGetAgain(false);
|
||||
//console.log(`psss : ${poss.length}`);
|
||||
};
|
||||
fetchData();
|
||||
}
|
||||
if (true && group.current.userData.counter < poss.length) {
|
||||
group.current.position.set(
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.x / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.y / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.z / distanceScaleFactor
|
||||
)
|
||||
);
|
||||
//console.log(group.current.userData.counter);
|
||||
group.current.userData.counter++;
|
||||
}
|
||||
}, []);
|
||||
|
||||
const changeSpeed = (newSpeed) => {
|
||||
setPos(poss.slice(0, group.current.userData.counter + 10));
|
||||
setGetAgain(true);
|
||||
console.log(poss);
|
||||
setSpeed(newSpeed);
|
||||
};
|
||||
|
||||
customData.current["changeMercurySpeed"] = changeSpeed;
|
||||
|
||||
const col = useLoader(TextureLoader, "../img/mercury/mercurymap.jpg");
|
||||
const bump = useLoader(TextureLoader, "../img/mercury/mercurybump.jpg");
|
||||
return (
|
||||
<>
|
||||
<PlanetPath
|
||||
linePos={poss}
|
||||
planet={group}
|
||||
color={"#a34f5f"}
|
||||
lineLength={20}
|
||||
/>
|
||||
<group ref={group}>
|
||||
<PlanetOverlay planet={group} />
|
||||
<mesh ref={mercury}>
|
||||
<sphereGeometry args={[2439.7 / 6000, 50, 50]} />
|
||||
<meshPhongMaterial map={col} bumpMap={bump} bumpScale={0.3} />
|
||||
</mesh>
|
||||
</group>
|
||||
</>
|
||||
);
|
||||
};
|
||||
131
src/neptune.jsx
Normal file
|
|
@ -0,0 +1,131 @@
|
|||
import {
|
||||
Canvas,
|
||||
extend,
|
||||
useFrame,
|
||||
useLoader,
|
||||
useThree,
|
||||
} from "@react-three/fiber";
|
||||
import {
|
||||
shaderMaterial,
|
||||
OrbitControls,
|
||||
Line,
|
||||
Html,
|
||||
Text,
|
||||
} from "@react-three/drei";
|
||||
import React, {
|
||||
useRef,
|
||||
Suspense,
|
||||
useLayoutEffect,
|
||||
useState,
|
||||
useEffect,
|
||||
useContext,
|
||||
} from "react";
|
||||
import * as THREE from "three";
|
||||
import glsl from "glslify";
|
||||
import { TextureLoader } from "three/src/loaders/TextureLoader";
|
||||
import {
|
||||
Selection,
|
||||
Select,
|
||||
EffectComposer,
|
||||
Outline,
|
||||
Scanline,
|
||||
} from "@react-three/postprocessing";
|
||||
import "./styles.css";
|
||||
import { PlanetInfo } from "./planetInfo";
|
||||
|
||||
import { PlanetOverlay } from "./planetOverlay";
|
||||
import { PlanetPath } from "./path";
|
||||
import { MyContext } from "./Scene3";
|
||||
|
||||
export const Neptune = ({ positions }) => {
|
||||
const [poss, setPos] = useState([]);
|
||||
const [lineposs, setLinePos] = useState([]);
|
||||
const [getAgain, setGetAgain] = useState(false);
|
||||
const [speed, setSpeed] = useState(60);
|
||||
let distanceScaleFactor = 1000000;
|
||||
const neptune = useRef();
|
||||
const group = useRef();
|
||||
|
||||
const firstRef = useRef(true);
|
||||
let linePoss = [];
|
||||
const { customData } = useContext(MyContext);
|
||||
|
||||
useLayoutEffect(() => {
|
||||
group.current.userData.counter = 0;
|
||||
group.current.userData.name = "Neptune";
|
||||
group.current.userData.nearOvOp = 500;
|
||||
group.current.userData.scolor = "darkblue";
|
||||
}, []);
|
||||
|
||||
useFrame(() => {
|
||||
if (poss.length % 1000 == 0) {
|
||||
setPos(poss.slice(0, 500));
|
||||
}
|
||||
let date;
|
||||
if (firstRef.current) {
|
||||
date = new Date(Date.now());
|
||||
date.setMilliseconds(0);
|
||||
date.setSeconds(0);
|
||||
}
|
||||
//console.log(poss.length);
|
||||
//console.log(group.current.userData.counter);
|
||||
if (group.current.userData.counter % 250 == 0 || getAgain) {
|
||||
if (!firstRef.current)
|
||||
date = new Date(poss[poss.length - 1].date).toUTCString();
|
||||
const fetchData = async () => {
|
||||
let res = await fetch(
|
||||
`http://127.0.0.1:8000/duration/neptune?date=${date}&speed=${speed}` //example and simple data
|
||||
);
|
||||
let response = await res.json();
|
||||
|
||||
setPos(poss.concat(response)); // parse json
|
||||
firstRef.current = false;
|
||||
setGetAgain(false);
|
||||
//console.log(`psss : ${poss.length}`);
|
||||
};
|
||||
fetchData();
|
||||
}
|
||||
if (true && group.current.userData.counter < poss.length) {
|
||||
group.current.position.set(
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.x / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.y / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.z / distanceScaleFactor
|
||||
)
|
||||
);
|
||||
//console.log(group.current.userData.counter);
|
||||
group.current.userData.counter++;
|
||||
}
|
||||
}, []);
|
||||
|
||||
const changeSpeed = (newSpeed) => {
|
||||
setPos(poss.slice(0, group.current.userData.counter + 10));
|
||||
setGetAgain(true);
|
||||
console.log(poss);
|
||||
setSpeed(newSpeed);
|
||||
};
|
||||
|
||||
customData.current["changeNeptuneSpeed"] = changeSpeed;
|
||||
const col = useLoader(TextureLoader, "../img/neptune/neptunemap.jpg");
|
||||
return (
|
||||
<>
|
||||
<PlanetPath
|
||||
linePos={poss}
|
||||
planet={group}
|
||||
color={"darkblue"}
|
||||
lineLength={20}
|
||||
/>
|
||||
<group ref={group}>
|
||||
<PlanetOverlay planet={group} />
|
||||
<mesh ref={neptune}>
|
||||
<sphereGeometry args={[24622 / 6000, 50, 50]} />
|
||||
<meshPhongMaterial map={col} />
|
||||
</mesh>
|
||||
</group>
|
||||
</>
|
||||
);
|
||||
};
|
||||
1
src/overlay.jsx
Normal file
|
|
@ -0,0 +1 @@
|
|||
|
||||
107
src/path.jsx
Normal file
|
|
@ -0,0 +1,107 @@
|
|||
import { Canvas, extend, useFrame, useLoader } from "@react-three/fiber";
|
||||
import { shaderMaterial, OrbitControls, Line } from "@react-three/drei";
|
||||
import React, {
|
||||
useRef,
|
||||
Suspense,
|
||||
useLayoutEffect,
|
||||
useEffect,
|
||||
useState,
|
||||
} from "react";
|
||||
import { useControls } from "leva";
|
||||
import * as THREE from "three";
|
||||
import glsl from "glslify";
|
||||
import { TextureLoader } from "three/src/loaders/TextureLoader";
|
||||
import { PlanetOverlay } from "./planetOverlay";
|
||||
|
||||
export const PlanetPath = ({
|
||||
positions,
|
||||
linePos,
|
||||
color,
|
||||
datas,
|
||||
lineLength,
|
||||
lineAt,
|
||||
planet,
|
||||
}) => {
|
||||
let distanceScaleFactor = 1000000;
|
||||
const otherPoints = useRef([]);
|
||||
const counter = useRef(0);
|
||||
const shiftCounter = useRef(0);
|
||||
const [points, setPoints] = useState([]);
|
||||
|
||||
/*const points = positions.map(
|
||||
(pos) =>
|
||||
new THREE.Vector3(
|
||||
pos.x / distanceScaleFactor,
|
||||
pos.y / distanceScaleFactor,
|
||||
pos.z / distanceScaleFactor
|
||||
)
|
||||
);*/
|
||||
const lineref = useRef();
|
||||
//if (lineref) lineref.current.userData.counter = 0;
|
||||
|
||||
useLayoutEffect(() => {
|
||||
if (linePos) {
|
||||
for (var i = linePos.length - 1; i >= 0; i--) {
|
||||
otherPoints.current[i] = new THREE.Vector3(
|
||||
linePos[i].position.x / distanceScaleFactor,
|
||||
linePos[i].position.y / distanceScaleFactor,
|
||||
linePos[i].position.z / distanceScaleFactor
|
||||
);
|
||||
}
|
||||
}
|
||||
//console.log(otherPoints);
|
||||
});
|
||||
|
||||
useEffect(() => {}, []);
|
||||
|
||||
function getLength(arrV3) {
|
||||
let sum = 0;
|
||||
for (var i = 0; i < arrV3.length - 1; i += 2) {
|
||||
sum += arrV3[i].distanceTo(arrV3[i + 1]);
|
||||
}
|
||||
return sum;
|
||||
}
|
||||
useFrame(() => {
|
||||
//console.log(planet);
|
||||
/* if (planet) {
|
||||
otherPoints.current.push(planet.current.position);
|
||||
//console.log(planet.current.position);
|
||||
}
|
||||
if (otherPoints.current.length > 0) {
|
||||
//console.log(otherPoints.current);
|
||||
//console.log(asd);
|
||||
lineref.current.geometry.setFromPoints(asd);
|
||||
lineref.current.geometry.setDrawRange(0, Infinity);
|
||||
|
||||
//console.log(otherPoints);
|
||||
}*/
|
||||
//console.log(otherPoints);
|
||||
//var start = 0;
|
||||
//if (counter.current > lineLength) start = counter.current - lineLength;
|
||||
var realpoints = otherPoints.current.slice(
|
||||
shiftCounter.current,
|
||||
counter.current
|
||||
);
|
||||
//console.log(getLength(realpoints));
|
||||
if (realpoints.length > 0) {
|
||||
lineref.current.geometry.setFromPoints(realpoints);
|
||||
if (getLength(realpoints) > lineLength) {
|
||||
//console.log("cut");
|
||||
shiftCounter.current++;
|
||||
//realpoints.shift();
|
||||
}
|
||||
}
|
||||
|
||||
lineref.current.geometry.setDrawRange(0, Infinity);
|
||||
counter.current++;
|
||||
//console.log(counter.current);
|
||||
});
|
||||
return (
|
||||
<>
|
||||
<line ref={lineref} frustumCulled={false}>
|
||||
<bufferGeometry />
|
||||
<lineBasicMaterial color={color} />
|
||||
</line>
|
||||
</>
|
||||
);
|
||||
};
|
||||
79
src/planetInfo.jsx
Normal file
|
|
@ -0,0 +1,79 @@
|
|||
import {
|
||||
Canvas,
|
||||
extend,
|
||||
useFrame,
|
||||
useLoader,
|
||||
useThree,
|
||||
} from "@react-three/fiber";
|
||||
import {
|
||||
shaderMaterial,
|
||||
OrbitControls,
|
||||
Line,
|
||||
Html,
|
||||
Text,
|
||||
} from "@react-three/drei";
|
||||
import React, {
|
||||
useRef,
|
||||
Suspense,
|
||||
useLayoutEffect,
|
||||
useState,
|
||||
useEffect,
|
||||
useContext,
|
||||
forwardRef,
|
||||
memo,
|
||||
} from "react";
|
||||
import { useNavigate } from "react-router-dom";
|
||||
import * as THREE from "three";
|
||||
import { MyContext } from "./Scene3";
|
||||
import saturnImage from "./saturn.jpg";
|
||||
|
||||
import "./styles.css";
|
||||
|
||||
import PropTypes from "prop-types";
|
||||
|
||||
export const PlanetInfo = memo(
|
||||
forwardRef(function PlanetInfo(props, ref) {
|
||||
const navigate = useNavigate();
|
||||
const [visibility, setVisibility] = useState("hidden");
|
||||
const { customData } = useContext(MyContext);
|
||||
const [planetData, setPlanetData] = useState({ name: "Default" });
|
||||
|
||||
useEffect(() => {
|
||||
const showInfo = (planet) => {
|
||||
if (planet && planet.name) setPlanetData({ name: planet.name });
|
||||
console.log(planetData);
|
||||
setVisibility("visible");
|
||||
};
|
||||
if (showInfo) customData.current["showInfo"] = showInfo;
|
||||
}, [customData, planetData]);
|
||||
|
||||
const someEventHandler = () => {
|
||||
navigate("/");
|
||||
};
|
||||
|
||||
function closeInfo() {
|
||||
setVisibility("hidden");
|
||||
}
|
||||
|
||||
return (
|
||||
<div className="planetInfo" style={{ visibility: visibility }}>
|
||||
<div className="wrapper">
|
||||
<h1>{planetData.name}</h1>
|
||||
<img src={saturnImage}></img>
|
||||
<p>
|
||||
Adorned with a dazzling, complex system of icy rings, Saturn is
|
||||
unique in our solar system. The other giant planets have rings, but
|
||||
none are as spectacular as Saturn's.
|
||||
</p>
|
||||
<button type="button" onClick={closeInfo}>
|
||||
Visit
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
})
|
||||
);
|
||||
|
||||
PlanetInfo.propTypes = {
|
||||
planet: PropTypes.object,
|
||||
};
|
||||
133
src/planetOverlay.jsx
Normal file
|
|
@ -0,0 +1,133 @@
|
|||
import {
|
||||
Canvas,
|
||||
extend,
|
||||
useFrame,
|
||||
useLoader,
|
||||
useThree,
|
||||
} from "@react-three/fiber";
|
||||
import {
|
||||
shaderMaterial,
|
||||
OrbitControls,
|
||||
Line,
|
||||
Html,
|
||||
Text,
|
||||
} from "@react-three/drei";
|
||||
import React, {
|
||||
useRef,
|
||||
Suspense,
|
||||
useLayoutEffect,
|
||||
useState,
|
||||
useEffect,
|
||||
useContext,
|
||||
} from "react";
|
||||
import * as THREE from "three";
|
||||
import { MyContext } from "./Scene3";
|
||||
|
||||
import "./styles.css";
|
||||
|
||||
import PropTypes from "prop-types";
|
||||
|
||||
export const PlanetOverlay = ({ planet }) => {
|
||||
const ref = useRef();
|
||||
let [opacity, setOpacity] = useState(0);
|
||||
let [minDistance, setMinDistance] = useState(0);
|
||||
let [scolor, setSColor] = useState("white");
|
||||
let [follow, setFollow] = useState(false);
|
||||
const { camera } = useThree();
|
||||
const [name, setName] = useState("Undefined");
|
||||
const svgStyle = { height: "20px", width: "20px", stroke: scolor };
|
||||
var { controls } = useContext(MyContext);
|
||||
const { customData } = useContext(MyContext);
|
||||
|
||||
const handleClick = React.useCallback(
|
||||
(event) => {
|
||||
// prevent context menu from opening on right-click
|
||||
event.preventDefault();
|
||||
|
||||
// synthetic event
|
||||
/*switch (event.type) {
|
||||
case "click":
|
||||
message = `Left click (synthetic event)`;
|
||||
break;
|
||||
case "contextmenu":
|
||||
message = `Right click (synthetic event)`;
|
||||
break;
|
||||
}*/
|
||||
|
||||
// native event
|
||||
switch (event.nativeEvent.button) {
|
||||
case 0:
|
||||
controls.current.target.copy(planet.current.position.clone());
|
||||
customData.current.showInfo(planet.current.userData);
|
||||
console.log(customData);
|
||||
//startFollow();
|
||||
break;
|
||||
case 2:
|
||||
//endFollow();
|
||||
break;
|
||||
}
|
||||
},
|
||||
[controls, planet, customData]
|
||||
);
|
||||
|
||||
useEffect(() => {
|
||||
setName(planet.current.userData.name);
|
||||
setMinDistance(planet.current.userData.nearOvOp);
|
||||
setSColor(planet.current.userData.scolor);
|
||||
}, [planet, name, minDistance, customData]);
|
||||
|
||||
useFrame(() => {
|
||||
var distance = camera.position.distanceTo(planet.current.position);
|
||||
if (distance < minDistance) {
|
||||
setOpacity(0);
|
||||
} else {
|
||||
setOpacity(1);
|
||||
}
|
||||
if (follow && controls) {
|
||||
controls.current.target.copy(planet.current.position.clone());
|
||||
controls.current.maxDistance = 20;
|
||||
}
|
||||
}, []);
|
||||
|
||||
function startFollow() {
|
||||
console.log(ref === ref);
|
||||
setFollow(true);
|
||||
}
|
||||
|
||||
function endFollow() {
|
||||
setFollow(false);
|
||||
controls.current.reset();
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
<Html
|
||||
ref={ref}
|
||||
zIndexRange={[11, 0]}
|
||||
className="overlay"
|
||||
style={{ opacity: opacity }}
|
||||
>
|
||||
<div className="wrapper">
|
||||
<span
|
||||
className="icon"
|
||||
onClick={handleClick}
|
||||
onContextMenu={handleClick}
|
||||
>
|
||||
<svg
|
||||
onMouseEnter={() => setSColor("blue")}
|
||||
onMouseLeave={() => setSColor(planet.current.userData.scolor)}
|
||||
style={svgStyle}
|
||||
>
|
||||
<circle cx="10" cy="10" r="9" strokeWidth="1" fill="none" />
|
||||
</svg>
|
||||
</span>
|
||||
<span className="content">{name}</span>
|
||||
</div>
|
||||
</Html>
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
PlanetOverlay.propTypes = {
|
||||
planet: PropTypes.object,
|
||||
};
|
||||
BIN
src/saturn.jpg
Normal file
|
After Width: | Height: | Size: 14 KiB |
167
src/saturn.jsx
Normal file
|
|
@ -0,0 +1,167 @@
|
|||
import { Canvas, extend, useFrame, useLoader } from "@react-three/fiber";
|
||||
import { shaderMaterial, OrbitControls, Line } from "@react-three/drei";
|
||||
import React, {
|
||||
useRef,
|
||||
Suspense,
|
||||
useLayoutEffect,
|
||||
useState,
|
||||
useContext,
|
||||
} from "react";
|
||||
import * as THREE from "three";
|
||||
import glsl from "glslify";
|
||||
import { TextureLoader } from "three/src/loaders/TextureLoader";
|
||||
import { PlanetOverlay } from "./planetOverlay";
|
||||
import { PlanetPath } from "./path";
|
||||
import { MyContext } from "./Scene3";
|
||||
|
||||
const SaturnRingMaterial = shaderMaterial(
|
||||
{
|
||||
ringCol: 0,
|
||||
ringAlpha: 0,
|
||||
innerRadius: 58232 / 6000 + 0,
|
||||
outerRadius: 58232 / 6000 + 0,
|
||||
},
|
||||
glsl`
|
||||
varying vec3 vPos;
|
||||
|
||||
void main() {
|
||||
vPos = position;
|
||||
vec3 viewPosition = (modelViewMatrix * vec4(position, 1.)).xyz;
|
||||
gl_Position = projectionMatrix * vec4(viewPosition, 1.);
|
||||
}
|
||||
`,
|
||||
glsl`
|
||||
uniform sampler2D ringCol;
|
||||
uniform sampler2D ringAlpha;
|
||||
uniform float innerRadius;
|
||||
uniform float outerRadius;
|
||||
|
||||
varying vec3 vPos;
|
||||
|
||||
vec4 color() {
|
||||
vec2 uv = vec2(0);
|
||||
uv.x = (length(vPos) - innerRadius) / (innerRadius + outerRadius);
|
||||
|
||||
vec4 pixel = texture2D(ringCol, uv);
|
||||
vec4 pixel2 = texture2D(ringAlpha, uv);
|
||||
pixel[3] = pixel2[0];
|
||||
if (pixel[3] <= 0.01) {
|
||||
discard;
|
||||
}
|
||||
return pixel;
|
||||
}
|
||||
|
||||
void main() {
|
||||
gl_FragColor = color();
|
||||
}
|
||||
`
|
||||
);
|
||||
|
||||
extend({ SaturnRingMaterial });
|
||||
|
||||
export const Saturn = ({ positions }) => {
|
||||
const [poss, setPos] = useState([]);
|
||||
const [lineposs, setLinePos] = useState([]);
|
||||
const [getAgain, setGetAgain] = useState(false);
|
||||
const [speed, setSpeed] = useState(60);
|
||||
const saturn = useRef("saturn");
|
||||
const group = useRef("group");
|
||||
const col = useLoader(TextureLoader, "../img/saturn/saturnmap.jpg");
|
||||
const ringCol = useLoader(TextureLoader, "../img/saturn/saturnringcolor.jpg");
|
||||
const ringAlpha = useLoader(
|
||||
TextureLoader,
|
||||
"../img/saturn/saturnringpattern.gif"
|
||||
);
|
||||
let distanceScaleFactor = 1000000;
|
||||
|
||||
const firstRef = useRef(true);
|
||||
let linePoss = [];
|
||||
const { customData } = useContext(MyContext);
|
||||
|
||||
useLayoutEffect(() => {
|
||||
group.current.userData.counter = 0;
|
||||
group.current.userData.name = "Saturn";
|
||||
group.current.userData.nearOvOp = 800;
|
||||
group.current.userData.scolor = "red";
|
||||
}, []);
|
||||
|
||||
useFrame(() => {
|
||||
if (poss.length % 1000 == 0) {
|
||||
setPos(poss.slice(0, 500));
|
||||
}
|
||||
let date;
|
||||
if (firstRef.current) {
|
||||
date = new Date(Date.now());
|
||||
date.setMilliseconds(0);
|
||||
date.setSeconds(0);
|
||||
}
|
||||
//console.log(poss.length);
|
||||
//console.log(group.current.userData.counter);
|
||||
if (group.current.userData.counter % 250 == 0 || getAgain) {
|
||||
if (!firstRef.current)
|
||||
date = new Date(poss[poss.length - 1].date).toUTCString();
|
||||
const fetchData = async () => {
|
||||
let res = await fetch(
|
||||
`http://127.0.0.1:8000/duration/saturn?date=${date}&speed=${speed}` //example and simple data
|
||||
);
|
||||
let response = await res.json();
|
||||
|
||||
setPos(poss.concat(response)); // parse json
|
||||
firstRef.current = false;
|
||||
setGetAgain(false);
|
||||
//console.log(`psss : ${poss.length}`);
|
||||
};
|
||||
fetchData();
|
||||
}
|
||||
if (true && group.current.userData.counter < poss.length) {
|
||||
group.current.position.set(
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.x / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.y / distanceScaleFactor
|
||||
),
|
||||
Number(
|
||||
poss[group.current.userData.counter].position.z / distanceScaleFactor
|
||||
)
|
||||
);
|
||||
//console.log(group.current.userData.counter);
|
||||
group.current.userData.counter++;
|
||||
}
|
||||
}, []);
|
||||
|
||||
const changeSpeed = (newSpeed) => {
|
||||
setPos(poss.slice(0, group.current.userData.counter + 10));
|
||||
setGetAgain(true);
|
||||
console.log(poss);
|
||||
setSpeed(newSpeed);
|
||||
};
|
||||
|
||||
customData.current["changeSaturnSpeed"] = changeSpeed;
|
||||
return (
|
||||
<>
|
||||
<PlanetPath
|
||||
linePos={poss}
|
||||
planet={group}
|
||||
color={"red"}
|
||||
lineLength={100}
|
||||
/>
|
||||
<group ref={group}>
|
||||
<PlanetOverlay planet={group} />
|
||||
<mesh ref={saturn}>
|
||||
<sphereGeometry args={[58232 / 6000, 50, 50]} />
|
||||
<meshPhongMaterial map={col} />
|
||||
</mesh>
|
||||
<mesh>
|
||||
<ringGeometry args={[58232 / 6000 + 1, 58232 / 6000 + 5, 100, 100]} />
|
||||
<saturnRingMaterial
|
||||
ringCol={ringCol}
|
||||
ringAlpha={ringAlpha}
|
||||
transparent={true}
|
||||
side={THREE.DoubleSide}
|
||||
/>
|
||||
</mesh>
|
||||
</group>
|
||||
</>
|
||||
);
|
||||
};
|
||||
46
src/skybox.jsx
Normal file
|
|
@ -0,0 +1,46 @@
|
|||
import { Canvas, useFrame, useThree } from "@react-three/fiber";
|
||||
import { OrbitControls, PerspectiveCamera } from "@react-three/drei";
|
||||
import React, {
|
||||
Suspense,
|
||||
useState,
|
||||
useEffect,
|
||||
useRef,
|
||||
createContext,
|
||||
useContext,
|
||||
forwardRef,
|
||||
memo,
|
||||
useMemo,
|
||||
} from "react";
|
||||
import { Earth } from "./earth.jsx";
|
||||
import { Mars } from "./mars.jsx";
|
||||
import { Jupiter } from "./jupiter.jsx";
|
||||
import { Saturn } from "./saturn.jsx";
|
||||
import { Mercury } from "./mercury.jsx";
|
||||
import { Venus } from "./venus.jsx";
|
||||
import { Neptune } from "./neptune.jsx";
|
||||
import { Uranus } from "./uranus.jsx";
|
||||
import { Sun } from "./sun.jsx";
|
||||
import * as THREE from "three";
|
||||
import { PlanetInfo } from "./planetInfo.jsx";
|
||||
import {
|
||||
Selection,
|
||||
Select,
|
||||
EffectComposer,
|
||||
Outline,
|
||||
} from "@react-three/postprocessing";
|
||||
|
||||
export const Skybox = () => {
|
||||
const { scene } = useThree();
|
||||
const loader = new THREE.CubeTextureLoader();
|
||||
const box = loader.load([
|
||||
"../img/front.png",
|
||||
"../img/back.png",
|
||||
"../img/top.png",
|
||||
"../img/bottom.png",
|
||||
"../img/left.png",
|
||||
"../img/right.png",
|
||||
]);
|
||||
scene.background = box;
|
||||
|
||||
return <></>;
|
||||
};
|
||||
71
src/styles.css
Normal file
|
|
@ -0,0 +1,71 @@
|
|||
.overlay .wrapper {
|
||||
transform: translate3d(-10px, -10px, 0);
|
||||
position: absolute;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
canvas {
|
||||
background-color: black;
|
||||
}
|
||||
|
||||
.overlay .wrapper .content {
|
||||
position: absolute;
|
||||
color: rgb(254, 254, 254);
|
||||
font-size: 1.05em;
|
||||
font-family: Arial, Helvetica, sans-serif;
|
||||
user-select: none;
|
||||
background-size: contain;
|
||||
}
|
||||
|
||||
.overlay .wrapper .icon {
|
||||
/*background-image: url(../ring.svg);
|
||||
background-repeat: no-repeat;
|
||||
background-size: contain;
|
||||
stroke: red;
|
||||
|
||||
height: 20px;
|
||||
width: 20px;
|
||||
top: 10px;*/
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
display: block;
|
||||
}
|
||||
|
||||
.overlay {
|
||||
}
|
||||
|
||||
.planetInfo {
|
||||
z-index: 12;
|
||||
position: absolute;
|
||||
height: 100%;
|
||||
/*background-color: aliceblue;*/
|
||||
}
|
||||
|
||||
.slidecontainer {
|
||||
position: absolute;
|
||||
z-index: 12;
|
||||
top: 96%;
|
||||
right: 45%;
|
||||
}
|
||||
|
||||
.planetInfo .wrapper {
|
||||
background-color: rgba(194, 15, 15, 0);
|
||||
backdrop-filter: blur(0.5px);
|
||||
display: block;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
height: 100%;
|
||||
border-right: 1px solid rgba(255, 255, 255, 0.216);
|
||||
}
|
||||
|
||||
.planetInfo .wrapper p {
|
||||
color: white;
|
||||
padding: 2px;
|
||||
margin-left: 3%;
|
||||
}
|
||||
|
||||
.planetInfo .wrapper h1 {
|
||||
color: white;
|
||||
padding: 2px;
|
||||
margin-left: 3%;
|
||||
}
|
||||