Spaces:
Running
Running
Add 1 files
Browse files- index.html +131 -1
index.html
CHANGED
@@ -3,7 +3,7 @@
|
|
3 |
<head>
|
4 |
<meta charset="UTF-8">
|
5 |
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
6 |
-
<title>Système Solaire 3D</title>
|
7 |
<script src="https://cdn.tailwindcss.com"></script>
|
8 |
<script src="https://cdn.jsdelivr.net/npm/three@0.128.0/build/three.min.js"></script>
|
9 |
<script src="https://cdn.jsdelivr.net/npm/three@0.128.0/examples/js/controls/OrbitControls.js"></script>
|
@@ -79,6 +79,15 @@
|
|
79 |
backdrop-filter: blur(5px);
|
80 |
display: none;
|
81 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
82 |
</style>
|
83 |
</head>
|
84 |
<body>
|
@@ -102,6 +111,9 @@
|
|
102 |
<button id="toggleLabels" class="bg-purple-600 hover:bg-purple-700 text-white py-1 px-3 rounded text-sm transition">
|
103 |
Masquer les labels
|
104 |
</button>
|
|
|
|
|
|
|
105 |
</div>
|
106 |
</div>
|
107 |
|
@@ -377,11 +389,77 @@
|
|
377 |
labels.push({ element: label, planet: planet });
|
378 |
});
|
379 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
380 |
// Contrôles UI
|
381 |
const speedControl = document.getElementById('speedControl');
|
382 |
const speedValue = document.getElementById('speedValue');
|
383 |
const toggleOrbits = document.getElementById('toggleOrbits');
|
384 |
const toggleLabels = document.getElementById('toggleLabels');
|
|
|
385 |
const planetInfo = document.getElementById('planetInfo');
|
386 |
const planetName = document.getElementById('planetName');
|
387 |
const planetDistance = document.getElementById('planetDistance');
|
@@ -390,6 +468,7 @@
|
|
390 |
|
391 |
let showOrbits = true;
|
392 |
let showLabels = true;
|
|
|
393 |
let speedFactor = 1;
|
394 |
|
395 |
speedControl.addEventListener('input', (e) => {
|
@@ -408,11 +487,21 @@
|
|
408 |
toggleLabels.addEventListener('click', () => {
|
409 |
showLabels = !showLabels;
|
410 |
labels.forEach(label => label.element.style.display = showLabels ? 'block' : 'none');
|
|
|
411 |
toggleLabels.textContent = showLabels ? 'Masquer les labels' : 'Afficher les labels';
|
412 |
toggleLabels.classList.toggle('bg-purple-600');
|
413 |
toggleLabels.classList.toggle('bg-gray-600');
|
414 |
});
|
415 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
416 |
// Gestion des clics sur les planètes
|
417 |
window.addEventListener('click', (event) => {
|
418 |
// Calcul de la position de la souris en coordonnées normalisées
|
@@ -468,6 +557,12 @@
|
|
468 |
const y = (-(screenPosition.y * 0.5 + 0.5) + 1) * window.innerHeight;
|
469 |
label.element.style.transform = `translate(-50%, -50%) translate(${x}px,${y}px)`;
|
470 |
});
|
|
|
|
|
|
|
|
|
|
|
|
|
471 |
|
472 |
// Animation du soleil
|
473 |
sun.rotation.y += 0.002 * speedFactor;
|
@@ -486,6 +581,41 @@
|
|
486 |
particle.position.normalize().multiplyScalar(5 + Math.random() * 2);
|
487 |
}
|
488 |
});
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
489 |
|
490 |
controls.update();
|
491 |
renderer.render(scene, camera);
|
|
|
3 |
<head>
|
4 |
<meta charset="UTF-8">
|
5 |
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
6 |
+
<title>Système Solaire 3D avec Comète</title>
|
7 |
<script src="https://cdn.tailwindcss.com"></script>
|
8 |
<script src="https://cdn.jsdelivr.net/npm/three@0.128.0/build/three.min.js"></script>
|
9 |
<script src="https://cdn.jsdelivr.net/npm/three@0.128.0/examples/js/controls/OrbitControls.js"></script>
|
|
|
79 |
backdrop-filter: blur(5px);
|
80 |
display: none;
|
81 |
}
|
82 |
+
.comet-label {
|
83 |
+
position: absolute;
|
84 |
+
color: #aaf;
|
85 |
+
font-size: 12px;
|
86 |
+
pointer-events: none;
|
87 |
+
text-shadow: 0 0 3px black;
|
88 |
+
white-space: nowrap;
|
89 |
+
transform: translate(-50%, -50%);
|
90 |
+
}
|
91 |
</style>
|
92 |
</head>
|
93 |
<body>
|
|
|
111 |
<button id="toggleLabels" class="bg-purple-600 hover:bg-purple-700 text-white py-1 px-3 rounded text-sm transition">
|
112 |
Masquer les labels
|
113 |
</button>
|
114 |
+
<button id="toggleComet" class="bg-green-600 hover:bg-green-700 text-white py-1 px-3 rounded text-sm transition">
|
115 |
+
Masquer la comète
|
116 |
+
</button>
|
117 |
</div>
|
118 |
</div>
|
119 |
|
|
|
389 |
labels.push({ element: label, planet: planet });
|
390 |
});
|
391 |
|
392 |
+
// Création de la comète
|
393 |
+
function createComet() {
|
394 |
+
// Noyau de la comète
|
395 |
+
const cometGeometry = new THREE.SphereGeometry(0.3, 16, 16);
|
396 |
+
const cometMaterial = new THREE.MeshPhongMaterial({
|
397 |
+
color: 0x88ccff,
|
398 |
+
emissive: 0x88ccff,
|
399 |
+
emissiveIntensity: 0.5
|
400 |
+
});
|
401 |
+
const comet = new THREE.Mesh(cometGeometry, cometMaterial);
|
402 |
+
|
403 |
+
// Queue de la comète (particules)
|
404 |
+
const tailParticles = new THREE.BufferGeometry();
|
405 |
+
const tailMaterial = new THREE.PointsMaterial({
|
406 |
+
color: 0x88ffff,
|
407 |
+
size: 0.1,
|
408 |
+
transparent: true,
|
409 |
+
opacity: 0.8,
|
410 |
+
blending: THREE.AdditiveBlending
|
411 |
+
});
|
412 |
+
|
413 |
+
const tailVertices = [];
|
414 |
+
for (let i = 0; i < 100; i++) {
|
415 |
+
// Position aléatoire derrière la comète
|
416 |
+
const x = -Math.random() * 5;
|
417 |
+
const y = (Math.random() - 0.5) * 0.5;
|
418 |
+
const z = (Math.random() - 0.5) * 0.5;
|
419 |
+
tailVertices.push(x, y, z);
|
420 |
+
}
|
421 |
+
|
422 |
+
tailParticles.setAttribute('position', new THREE.Float32BufferAttribute(tailVertices, 3));
|
423 |
+
const tail = new THREE.Points(tailParticles, tailMaterial);
|
424 |
+
comet.add(tail);
|
425 |
+
|
426 |
+
// Position initiale aléatoire
|
427 |
+
const angle = Math.random() * Math.PI * 2;
|
428 |
+
const distance = 150 + Math.random() * 50;
|
429 |
+
comet.position.x = Math.cos(angle) * distance;
|
430 |
+
comet.position.z = Math.sin(angle) * distance;
|
431 |
+
comet.position.y = (Math.random() - 0.5) * 30;
|
432 |
+
|
433 |
+
// Vitesse et direction aléatoires
|
434 |
+
const velocity = new THREE.Vector3(
|
435 |
+
(Math.random() - 0.5) * 0.5,
|
436 |
+
(Math.random() - 0.5) * 0.2,
|
437 |
+
(Math.random() - 0.5) * 0.5
|
438 |
+
);
|
439 |
+
|
440 |
+
// Label pour la comète
|
441 |
+
const label = document.createElement('div');
|
442 |
+
label.className = 'comet-label';
|
443 |
+
label.textContent = 'Comète';
|
444 |
+
document.body.appendChild(label);
|
445 |
+
|
446 |
+
return {
|
447 |
+
mesh: comet,
|
448 |
+
velocity: velocity,
|
449 |
+
label: label,
|
450 |
+
tail: tail
|
451 |
+
};
|
452 |
+
}
|
453 |
+
|
454 |
+
const comet = createComet();
|
455 |
+
scene.add(comet.mesh);
|
456 |
+
|
457 |
// Contrôles UI
|
458 |
const speedControl = document.getElementById('speedControl');
|
459 |
const speedValue = document.getElementById('speedValue');
|
460 |
const toggleOrbits = document.getElementById('toggleOrbits');
|
461 |
const toggleLabels = document.getElementById('toggleLabels');
|
462 |
+
const toggleComet = document.getElementById('toggleComet');
|
463 |
const planetInfo = document.getElementById('planetInfo');
|
464 |
const planetName = document.getElementById('planetName');
|
465 |
const planetDistance = document.getElementById('planetDistance');
|
|
|
468 |
|
469 |
let showOrbits = true;
|
470 |
let showLabels = true;
|
471 |
+
let showComet = true;
|
472 |
let speedFactor = 1;
|
473 |
|
474 |
speedControl.addEventListener('input', (e) => {
|
|
|
487 |
toggleLabels.addEventListener('click', () => {
|
488 |
showLabels = !showLabels;
|
489 |
labels.forEach(label => label.element.style.display = showLabels ? 'block' : 'none');
|
490 |
+
comet.label.style.display = showLabels ? 'block' : 'none';
|
491 |
toggleLabels.textContent = showLabels ? 'Masquer les labels' : 'Afficher les labels';
|
492 |
toggleLabels.classList.toggle('bg-purple-600');
|
493 |
toggleLabels.classList.toggle('bg-gray-600');
|
494 |
});
|
495 |
|
496 |
+
toggleComet.addEventListener('click', () => {
|
497 |
+
showComet = !showComet;
|
498 |
+
comet.mesh.visible = showComet;
|
499 |
+
comet.label.style.display = showComet && showLabels ? 'block' : 'none';
|
500 |
+
toggleComet.textContent = showComet ? 'Masquer la comète' : 'Afficher la comète';
|
501 |
+
toggleComet.classList.toggle('bg-green-600');
|
502 |
+
toggleComet.classList.toggle('bg-gray-600');
|
503 |
+
});
|
504 |
+
|
505 |
// Gestion des clics sur les planètes
|
506 |
window.addEventListener('click', (event) => {
|
507 |
// Calcul de la position de la souris en coordonnées normalisées
|
|
|
557 |
const y = (-(screenPosition.y * 0.5 + 0.5) + 1) * window.innerHeight;
|
558 |
label.element.style.transform = `translate(-50%, -50%) translate(${x}px,${y}px)`;
|
559 |
});
|
560 |
+
|
561 |
+
// Mise à jour du label de la comète
|
562 |
+
const cometScreenPos = comet.mesh.position.clone().project(camera);
|
563 |
+
const cometX = (cometScreenPos.x * 0.5 + 0.5) * window.innerWidth;
|
564 |
+
const cometY = (-(cometScreenPos.y * 0.5 + 0.5) + 1) * window.innerHeight;
|
565 |
+
comet.label.style.transform = `translate(-50%, -50%) translate(${cometX}px,${cometY}px)`;
|
566 |
|
567 |
// Animation du soleil
|
568 |
sun.rotation.y += 0.002 * speedFactor;
|
|
|
581 |
particle.position.normalize().multiplyScalar(5 + Math.random() * 2);
|
582 |
}
|
583 |
});
|
584 |
+
|
585 |
+
// Animation de la comète
|
586 |
+
comet.mesh.position.x += comet.velocity.x * speedFactor;
|
587 |
+
comet.mesh.position.y += comet.velocity.y * speedFactor;
|
588 |
+
comet.mesh.position.z += comet.velocity.z * speedFactor;
|
589 |
+
|
590 |
+
// Faire tourner la queue de la comète
|
591 |
+
comet.tail.rotation.y += 0.01 * speedFactor;
|
592 |
+
|
593 |
+
// Si la comète sort de la scène, la repositionner de l'autre côté
|
594 |
+
if (Math.abs(comet.mesh.position.x) > 200 ||
|
595 |
+
Math.abs(comet.mesh.position.y) > 100 ||
|
596 |
+
Math.abs(comet.mesh.position.z) > 200) {
|
597 |
+
|
598 |
+
// Nouvelle position aléatoire
|
599 |
+
const angle = Math.random() * Math.PI * 2;
|
600 |
+
const distance = 150 + Math.random() * 50;
|
601 |
+
comet.mesh.position.x = Math.cos(angle) * distance;
|
602 |
+
comet.mesh.position.z = Math.sin(angle) * distance;
|
603 |
+
comet.mesh.position.y = (Math.random() - 0.5) * 30;
|
604 |
+
|
605 |
+
// Nouvelle direction
|
606 |
+
comet.velocity.set(
|
607 |
+
(Math.random() - 0.5) * 0.5,
|
608 |
+
(Math.random() - 0.5) * 0.2,
|
609 |
+
(Math.random() - 0.5) * 0.5
|
610 |
+
);
|
611 |
+
}
|
612 |
+
|
613 |
+
// Orientation de la comète vers sa direction de mouvement
|
614 |
+
comet.mesh.lookAt(
|
615 |
+
comet.mesh.position.x + comet.velocity.x,
|
616 |
+
comet.mesh.position.y + comet.velocity.y,
|
617 |
+
comet.mesh.position.z + comet.velocity.z
|
618 |
+
);
|
619 |
|
620 |
controls.update();
|
621 |
renderer.render(scene, camera);
|