Meta Description" name="description" />

Share this result

Previews are deleted daily. Get a permanent share link sent to your inbox:
Script
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0, user-scalable=no"> <title>3D War Realistic</title> <style> body { margin:0; overflow:hidden; background:black; touch-action:none; } canvas { display:block; } /* Botones */ #attackBtn, #axeBtn{ position:absolute; width:75px; height:75px; border-radius:50%; text-align:center; line-height:75px; font-size:22px; color:white; opacity:0.9; } #attackBtn{ right:25px; bottom:60px; background:#8b0000; } #axeBtn{ right:120px; bottom:130px; background:#555; } /* Joystick visual */ #joystickBase{ position:absolute; left:40px; bottom:80px; width:120px; height:120px; border-radius:50%; background:rgba(255,255,255,0.1); } #joystickStick{ position:absolute; left:80px; bottom:120px; width:60px; height:60px; border-radius:50%; background:rgba(255,255,255,0.3); } </style> </head> <body> <div id="attackBtn">⚔</div> <div id="axeBtn">🪓</div> <div id="joystickBase"></div> <div id="joystickStick"></div> <script src="https://cdn.jsdelivr.net/npm/three@0.152.2/build/three.min.js"></script> <script> const scene = new THREE.Scene(); scene.background = new THREE.Color(0x101015); scene.fog = new THREE.Fog(0x000000, 10, 40); const camera = new THREE.PerspectiveCamera(70, window.innerWidth/window.innerHeight, 0.1, 1000); const renderer = new THREE.WebGLRenderer({antialias:true}); renderer.setSize(window.innerWidth, window.innerHeight); renderer.shadowMap.enabled = true; document.body.appendChild(renderer.domElement); // Luces const hemiLight = new THREE.HemisphereLight(0xffffff, 0x444444, 0.8); scene.add(hemiLight); const dirLight = new THREE.DirectionalLight(0xffffff,1); dirLight.position.set(5,10,7); dirLight.castShadow = true; scene.add(dirLight); // Suelo const floor = new THREE.Mesh( new THREE.PlaneGeometry(100,100), new THREE.MeshStandardMaterial({color:0x222222}) ); floor.rotation.x = -Math.PI/2; floor.receiveShadow = true; scene.add(floor); // ===== JUGADOR MÁS REALISTA ===== const player = new THREE.Group(); function createLimb(w,h,d,color,y){ const limb = new THREE.Mesh( new THREE.BoxGeometry(w,h,d), new THREE.MeshStandardMaterial({color}) ); limb.position.y = y; limb.castShadow = true; return limb; } // Cuerpo player.add(createLimb(1,2,0.6,0xaa0000,1.5)); // Cabeza player.add(createLimb(0.8,0.8,0.8,0xffcc99,3)); // Piernas player.add(createLimb(0.4,1.5,0.4,0x550000,0.75)); player.add(createLimb(0.4,1.5,0.4,0x550000,0.75)).position.x=0.6; // Brazos player.add(createLimb(0.4,1.5,0.4,0xaa0000,2)).position.x=-0.9; player.add(createLimb(0.4,1.5,0.4,0xaa0000,2)).position.x=0.9; scene.add(player); // ===== HACHA ===== const axe = new THREE.Mesh( new THREE.CylinderGeometry(0.1,0.1,2,8), new THREE.MeshStandardMaterial({color:0x8b4513}) ); axe.rotation.z=Math.PI/2; axe.visible=false; scene.add(axe); let axeState="idle"; let axeDir=new THREE.Vector3(); // ===== ENEMIGOS ===== let enemies=[]; function spawnEnemy(){ const enemy = createLimb(1,2,0.6,0x006600,1); enemy.position.set((Math.random()-0.5)*20,1,(Math.random()-0.5)*20); scene.add(enemy); enemies.push(enemy); } setInterval(spawnEnemy,3000); // ===== JOYSTICK ===== let joystick={dx:0,dy:0}; const stick=document.getElementById("joystickStick"); renderer.domElement.addEventListener("touchmove", e=>{ const t=e.touches[0]; if(t.clientX<200){ let dx=t.clientX-100; let dy=t.clientY-(window.innerHeight-140); let mag=Math.sqrt(dx*dx+dy*dy); if(mag>40){ dx/=mag; dy/=mag; } joystick.dx=dx/40; joystick.dy=dy/40; stick.style.left=(80+dx)+"px"; stick.style.bottom=(120-dy)+"px"; } }); renderer.domElement.addEventListener("touchend", ()=>{ joystick.dx=0; joystick.dy=0; stick.style.left="80px"; stick.style.bottom="120px"; }); // Ataque document.getElementById("attackBtn").addEventListener("touchstart", ()=>{ enemies.forEach((e,i)=>{ if(player.position.distanceTo(e.position)<3){ scene.remove(e); enemies.splice(i,1); } }); }); // Lanzar hacha document.getElementById("axeBtn").addEventListener("touchstart", ()=>{ if(axeState==="idle"){ axe.visible=true; axe.position.copy(player.position); axeDir.set(joystick.dx,0,joystick.dy).normalize(); if(axeDir.length()===0) axeDir.set(0,0,-1); axeState="forward"; } }); // Cámara camera.position.set(0,6,10); // Loop function animate(){ requestAnimationFrame(animate); player.position.x+=joystick.dx*0.2; player.position.z+=joystick.dy*0.2; enemies.forEach(e=>{ e.position.lerp(player.position,0.005); }); if(axeState==="forward"){ axe.position.addScaledVector(axeDir,0.6); if(axe.position.distanceTo(player.position)>8) axeState="return"; } else if(axeState==="return"){ let dir=new THREE.Vector3().subVectors(player.position,axe.position).normalize(); axe.position.addScaledVector(dir,0.7); if(axe.position.distanceTo(player.position)<1){ axeState="idle"; axe.visible=false; } } enemies.forEach((e,i)=>{ if(axe.visible && axe.position.distanceTo(e.position)<1.5){ scene.remove(e); enemies.splice(i,1); } }); camera.position.x=player.position.x; camera.position.z=player.position.z+10; camera.lookAt(player.position); renderer.render(scene,camera); } animate(); </script> </body> </html>
Landing Page
This ad does not have a landing page available
Network Timeline
Performance Summary

2

Requests

2

Domains

160KB

Transfer Size

624KB

Content Size

1,900.0ms

Dom Content Loaded

120.0ms

First Paint

1,900.0ms

Load Time
Domain Breakdown
Transfer Size (bytes)
Loading...
Content Size (bytes)
Loading...
Header Size (bytes)
Loading...
Requests
Loading...
Timings (ms)
Loading...
Total Time
Loading...
Content Breakdown
Transfer Size (bytes)
Loading...
Content Size (bytes)
Loading...
Header Size (bytes)
Loading...
Requests
Loading...