1- // Minimal JS for potential interactions (mobile menu, scrolling reveals)
21document . addEventListener ( 'DOMContentLoaded' , ( ) => {
3- console . log ( "B2B Automation Blog - System Ready" ) ;
4-
5- // Dynamic reveal animation on scroll for article cards
6- const observerOptions = {
7- threshold : 0.1
8- } ;
9-
2+ // Basic Intersection Observer for scroll animations
3+ const observerOptions = { threshold : 0.1 } ;
104 const observer = new IntersectionObserver ( ( entries ) => {
115 entries . forEach ( entry => {
126 if ( entry . isIntersecting ) {
@@ -22,4 +16,74 @@ document.addEventListener('DOMContentLoaded', () => {
2216 card . style . transition = 'all 0.6s ease-out' ;
2317 observer . observe ( card ) ;
2418 } ) ;
19+
20+ // --- THREE.JS INTERACTIVE SCENE ---
21+ const canvas = document . querySelector ( '#canvas3d' ) ;
22+ if ( ! canvas ) return ; // Only run on homepage
23+
24+ const scene = new THREE . Scene ( ) ;
25+
26+ // Setup camera
27+ const camera = new THREE . PerspectiveCamera ( 75 , window . innerWidth / window . innerHeight , 0.1 , 1000 ) ;
28+ camera . position . z = 5 ;
29+
30+ // Setup renderer
31+ const renderer = new THREE . WebGLRenderer ( { canvas : canvas , alpha : true , antialias : true } ) ;
32+ renderer . setSize ( window . innerWidth , window . innerHeight ) ;
33+ renderer . setPixelRatio ( Math . min ( window . devicePixelRatio , 2 ) ) ;
34+
35+ // Create Parametric Object (TorusKnot)
36+ const geometry = new THREE . TorusKnotGeometry ( 1.5 , 0.4 , 128 , 32 ) ;
37+
38+ // Create Material with wireframe
39+ const material = new THREE . MeshNormalMaterial ( {
40+ wireframe : true ,
41+ wireframeLinewidth : 2
42+ } ) ;
43+
44+ const torusKnot = new THREE . Mesh ( geometry , material ) ;
45+ scene . add ( torusKnot ) ;
46+
47+ // Mouse Interaction
48+ let mouseX = 0 ;
49+ let mouseY = 0 ;
50+ let targetX = 0 ;
51+ let targetY = 0 ;
52+ const windowHalfX = window . innerWidth / 2 ;
53+ const windowHalfY = window . innerHeight / 2 ;
54+
55+ document . addEventListener ( 'mousemove' , ( event ) => {
56+ mouseX = ( event . clientX - windowHalfX ) ;
57+ mouseY = ( event . clientY - windowHalfY ) ;
58+ } ) ;
59+
60+ // Animation Loop
61+ const clock = new THREE . Clock ( ) ;
62+
63+ function animate ( ) {
64+ requestAnimationFrame ( animate ) ;
65+ const elapsedTime = clock . getElapsedTime ( ) ;
66+
67+ // Base rotation
68+ torusKnot . rotation . x = elapsedTime * 0.2 ;
69+ torusKnot . rotation . y = elapsedTime * 0.3 ;
70+
71+ // Interactive rotation based on mouse
72+ targetX = mouseX * .001 ;
73+ targetY = mouseY * .001 ;
74+
75+ torusKnot . rotation . y += 0.05 * ( targetX - torusKnot . rotation . y ) ;
76+ torusKnot . rotation . x += 0.05 * ( targetY - torusKnot . rotation . x ) ;
77+
78+ renderer . render ( scene , camera ) ;
79+ }
80+
81+ animate ( ) ;
82+
83+ // Handle Resize
84+ window . addEventListener ( 'resize' , ( ) => {
85+ camera . aspect = window . innerWidth / window . innerHeight ;
86+ camera . updateProjectionMatrix ( ) ;
87+ renderer . setSize ( window . innerWidth , window . innerHeight ) ;
88+ } ) ;
2589} ) ;
0 commit comments