《Three.js 可操控3D魔方(键盘转动+打乱+复原)》
Three.js 可操控3D魔方键盘转动打乱复原直接复制整段HTML打开即可运行WASD/方向键控层旋转一键打乱、一键复原!DOCTYPEhtmlhtmllangzh-CNheadmetacharsetUTF-8titleThree.js 可玩3D魔方/titlestyle*{margin:0;padding:0;box-sizing:border-box;}body{overflow:hidden;background:#121218;font-family:sans-serif;}canvas{display:block;}.btn-box{position:fixed;top:20px;left:20px;z-index:999;}button{padding:8px 16px;margin:0 5px;border:none;border-radius:4px;cursor:pointer;background:#2563eb;color:#fff;}/style/headbodydivclassbtn-boxbuttonidrandomBtn打乱魔方/buttonbuttonidresetBtn一键复原/button/divscriptsrchttps://cdn.jsdelivr.net/npm/three0.158.0/build/three.min.js/scriptscriptsrchttps://cdn.jsdelivr.net/npm/three0.158.0/examples/js/controls/OrbitControls.js/scriptscript// 场景初始化constscenenewTHREE.Scene();scene.backgroundnewTHREE.Color(0x121218);constcameranewTHREE.PerspectiveCamera(60,innerWidth/innerHeight,0.1,200);camera.position.set(9,9,15);constrenderernewTHREE.WebGLRenderer({antialias:true});renderer.setSize(innerWidth,innerHeight);document.body.appendChild(renderer.domElement);// 视角控制器constcontrolsnewTHREE.OrbitControls(camera,renderer.domElement);controls.enableDampingtrue;// 灯光scene.add(newTHREE.AmbientLight(0xffffff,0.5));constdirLightnewTHREE.DirectionalLight(0xffffff,0.7);dirLight.position.set(15,20,10);scene.add(dirLight);// 魔方六色前、后、左、右、上、下constCOLORS[0xffffff,// 前白0xffff00,// 后黄0x0000ff,// 左蓝0xff0000,// 右红0x00ff00,// 上绿0xffa500// 下橙];constOFFSET1.06;letcubies[];letrubikRootnewTHREE.Group();// 创建单个魔方小块functioncreateCubie(x,y,z){constgeonewTHREE.BoxGeometry(1,1,1);constmatsCOLORS.map(cnewTHREE.MeshLambertMaterial({color:c}));constcubenewTHREE.Mesh(geo,mats);cube.userData{ox:x,oy:y,oz:z};cube.position.set(x*OFFSET,y*OFFSET,z*OFFSET);returncube;}// 生成完整3阶魔方functioninitRubik(){cubies[];rubikRoot.clear();for(letx-1;x1;x){for(lety-1;y1;y){for(letz-1;z1;z){letccreateCubie(x,y,z);cubies.push(c);rubikRoot.add(c);}}}scene.add(rubikRoot);}initRubik();// 旋转指定层functionrotateLayer(axis,idx,dir1){lettargetGroupnewTHREE.Group();lettargetList[];cubies.forEach(c{letposc.position;letval;if(axisx)valMath.round(pos.x/OFFSET);if(axisy)valMath.round(pos.y/OFFSET);if(axisz)valMath.round(pos.z/OFFSET);if(validx){targetList.push(c);rubikRoot.remove(c);targetGroup.add(c);}});scene.add(targetGroup);letangleMath.PI/2*dir;letrotObj{v:0};functionrotateAnimate(){if(rotObj.vangle){targetGroup.rotation[axis]angle;targetList.forEach(item{letwpnewTHREE.Vector3();item.getWorldPosition(wp);letqnewTHREE.Quaternion();item.getWorldQuaternion(q);rubikRoot.attach(item);item.position.copy(wp);item.quaternion.copy(q);});scene.remove(targetGroup);return;}rotObj.v0.15;targetGroup.rotation[axis]rotObj.v;requestAnimationFrame(rotateAnimate);}rotateAnimate();}// 键盘控制window.addEventListener(keydown,e{switch(e.key.toLowerCase()){casew:rotateLayer(y,1,1);break;// 上层右转cases:rotateLayer(y,-1,-1);break;// 下层左转casea:rotateLayer(x,-1,1);break;// 左层顺转cased:rotateLayer(x,1,-1);break;// 右层逆转caseq:rotateLayer(z,1,1);break;// 前层顺转casee:rotateLayer(z,-1,-1);break;// 后层逆转}});// 打乱魔方document.getElementById(randomBtn).onclick(){letops[()rotateLayer(y,1,1),()rotateLayer(y,-1,-1),()rotateLayer(x,1,-1),()rotateLayer(x,-1,1),()rotateLayer(z,1,1),()rotateLayer(z,-1,-1)];lettimes20;leti0;functionrandRun(){if(itimes)return;letfnops[Math.floor(Math.random()*ops.length)];fn();i;setTimeout(randRun,220);}randRun();};// 一键复原document.getElementById(resetBtn).onclick(){initRubik();};// 窗口适配window.onresize(){camera.aspectinnerWidth/innerHeight;camera.updateProjectionMatrix();renderer.setSize(innerWidth,innerHeight);};// 渲染循环functionanimate(){requestAnimationFrame(animate);controls.update();renderer.render(scene,camera);}animate();/script/body/html操作说明鼠标操作左键拖拽旋转视角滚轮缩放远近右键拖拽平移画面键盘按键控魔方转动W顶层向右旋转S底层向左旋转A左侧面顺时针转D右侧面逆时针转Q前面顺时针转E后面逆时针转按钮功能打乱魔方自动随机转动20步打乱一键复原瞬间重置回初始完整状态后续可加功能加入魔方还原算法自动求解加数字贴纸、边框黑线更逼真手机触屏滑动转层记录转动步数、计时闯关