ویرگول
ورودثبت نام
محمد حسین صادقی زاده
محمد حسین صادقی زاده
محمد حسین صادقی زاده
محمد حسین صادقی زاده
خواندن ۴ دقیقه·۱ ماه پیش

بازی زوبا

<!DOCTYPE html>

<html lang="fa" dir="rtl">

<head>

<meta charset="UTF-8">

<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no, viewport-fit=cover">

<title>🐾 زوبا ایرانی | نبرد قهرمانان | تمام لمسی</title>

<style>

*{margin:0;padding:0;box-sizing:border-box;-webkit-tap-highlight-color:transparent;}

body{

background:#0a0f08;

display:flex;justify-content:center;align-items:center;

height:100vh;overflow:hidden;

font-family:'Segoe UI',Tahoma,sans-serif;

touch-action:manipulation;

user-select:none;-webkit-user-select:none;

position:fixed;width:100%;

}

#game-wrapper{

position:relative;

width:100%;max-width:450px;

aspect-ratio:9/16;max-height:100vh;

border:3px solid #ffb020;

border-radius:20px;overflow:hidden;

box-shadow:0 0 50px rgba(255,140,0,0.5);

background:#2d5a1e;

}

canvas{display:block;width:100%;height:100%;}

#ui-layer{

position:absolute;top:8px;left:8px;right:8px;

display:flex;justify-content:space-between;

pointer-events:none;z-index:10;gap:6px;

}

.ui-box{

background:rgba(0,0,0,0.7);border:2px solid #e6a817;

border-radius:12px;padding:5px 10px;color:#ffd966;

font-weight:bold;font-size:13px;backdrop-filter:blur(4px);

text-align:center;min-width:65px;

}

.hp-outer{width:100%;height:6px;background:#331111;border-radius:8px;margin-top:3px;overflow:hidden;border:1px solid #a33;}

.hp-inner{height:100%;width:100%;background:linear-gradient(90deg,#f22,#f77);border-radius:8px;transition:width 0.2s;}

#hero-select{

position:absolute;top:0;left:0;width:100%;height:100%;

background:rgba(0,0,0,0.93);z-index:50;

display:flex;flex-direction:column;align-items:center;

justify-content:center;color:#ffcc44;overflow-y:auto;padding:20px;

}

#hero-select h2{font-size:22px;margin-bottom:4px;text-shadow:0 0 20px #ff8800;}

.hero-grid{display:flex;flex-wrap:wrap;gap:10px;justify-content:center;max-width:380px;margin-top:8px;}

.hero-card{

width:110px;height:140px;background:rgba(20,20,20,0.85);

border:3px solid #5a4a2a;border-radius:20px;

display:flex;flex-direction:column;align-items:center;

justify-content:center;cursor:pointer;transition:all 0.2s;

color:#ddd;font-weight:bold;font-size:12px;gap:5px;

}

.hero-card.selected{border-color:#ffcc00;box-shadow:0 0 30px #ffaa00;background:rgba(40,30,10,0.9);transform:scale(1.05);}

.hero-emoji{font-size:38px;}

.hero-stats{font-size:8px;color:#aaa;line-height:1.3;text-align:center;}

#start-btn{

margin-top:15px;padding:10px 40px;font-size:17px;

background:#ffaa00;border:none;border-radius:30px;

color:#0a0a0a;font-weight:bold;cursor:pointer;

box-shadow:0 0 25px #ff8800;

}

#mobile-controls{

position:absolute;bottom:20px;left:0;right:0;

z-index:20;display:flex;justify-content:space-between;

padding:0 15px;pointer-events:none;

}

#joystick-container{

width:90px;height:90px;pointer-events:auto;

position:relative;

}

#joystick-base{

width:90px;height:90px;border-radius:50%;

background:rgba(255,255,255,0.2);border:3px solid #ffbb44;

position:relative;backdrop-filter:blur(5px);

}

#joystick-thumb{

width:40px;height:40px;border-radius:50%;

background:rgba(255,200,80,0.8);

position:absolute;top:25px;left:25px;

transition:0.05s;pointer-events:none;

}

#right-buttons{

display:flex;flex-direction:column;gap:12px;pointer-events:auto;align-items:center;

}

#btn-special{

width:60px;height:60px;border-radius:50%;

background:rgba(138,43,226,0.5);border:3px solid #bb88ff;

font-size:26px;display:flex;align-items:center;justify-content:center;

backdrop-filter:blur(5px);color:white;

}

#btn-shoot{

width:70px;height:70px;border-radius:50%;

background:rgba(255,80,20,0.5);border:3px solid #ff8844;

font-size:30px;display:flex;align-items:center;justify-content:center;

backdrop-filter:blur(5px);color:white;

}

.cooldown-indicator{

position:absolute;font-size:20px;color:#fff;text-shadow:0 0 10px #000;

pointer-events:none;

}

#gameover-screen{

position:absolute;top:0;left:0;width:100%;height:100%;

background:rgba(0,0,0,0.85);z-index:40;

display:none;flex-direction:column;align-items:center;

justify-content:center;color:#ffd966;font-size:24px;font-weight:bold;

}

#gameover-screen button{

margin-top:18px;padding:10px 30px;font-size:17px;

background:#ffaa00;border:none;border-radius:30px;

font-weight:bold;cursor:pointer;

}

</style>

</head>

<body>

<div id="game-wrapper">

<canvas id="gameCanvas"></canvas>

<div id="ui-layer">

<div class="ui-box">⭐ <span id="scoreDisp">0</span><br>💀 <span id="killDisp">0</span></div>

<div class="ui-box" style="width:115px;">❤️ <span id="hpText">120</span>

<div class="hp-outer"><div class="hp-inner" id="hpFill"></div></div>

</div>

<div class="ui-box">⚡ <span id="specialDisp">آماده</span></div>

</div>

<div id="hero-select">

<h2>🐾 قهرمانت رو انتخاب کن</h2>

<div style="font-size:11px;color:#cca;margin-bottom:6px;">هر قهرمان قدرت منحصربهفرد داره</div>

<div class="hero-grid" id="heroGrid"></div>

<button id="start-btn">🎮 شروع نبرد!</button>

</div>

<div id="mobile-controls">

<div id="joystick-container">

<div id="joystick-base">

<div id="joystick-thumb"></div>

</div>

</div>

<div id="right-buttons">

<div id="btn-special">⚡</div>

<div id="btn-shoot">🔫</div>

</div>

</div>

<div id="gameover-screen">

<span>💔 شکست خوردی!</span>

<span style="font-size:14px;margin-top:5px;" id="finalScore"></span>

<button id="restartBtn">🔄 دوباره</button>

</div>

</div>

(function(){

const canvas=document.getElementById('gameCanvas');

const ctx=canvas.getContext('2d');

const W=450,H=800;

canvas.width=W;canvas.height=H;

const scoreDisp=document.getElementById('scoreDisp');

const killDisp=document.getElementById('killDisp');

const hpFill=document.getElementById('hpFill');

const hpText=document.getElementById('hpText');

const specialDisp=document.getElementById('specialDisp');

const heroSelectDiv=document.getElementById('hero-select');

const heroGrid=document.getElementById('heroGrid');

const startBtn=document.getElementById('start-btn');

const gameoverScreen=document.getElementById('gameover-screen');

const finalScoreSpan=document.getElementById('finalScore');

const restartBtn=document.getElementById('restartBtn');

const joyThumb=document.getElementById('joystick-thumb');

const joyBase=document.getElementById('joystick-base');

const btnSpecial=document.getElementById('btn-special');

const btnShoot=document.getElementById('btn-shoot');

let gameRunning=false,gameOver=false;

let score=0,kills=0;

let player,enemies=[],bullets=[],enemyBullets=[];

let enemySpawnTimer=0;

const MAP_W=2000,MAP_H=2000;

let bushes=[],walls=[],waters=[];

// Generate map

for(let i=0;i<120;i++) bushes.push({x:Math.random()*MAP_W,y:Math.random()*MAP_H,r:25+Math.random()*35});

for(let i=0;i<50;i++) walls.push({x:Math.random()*MAP_W,y:Math.random()*MAP_H,w:50+Math.random()*80,h:25+Math.random()*35});

for(let i=0;i<15;i++) waters.push({x:Math.random()*MAP_W,y:Math.random()*MAP_H,r:60+Math.random()*90});

const ALL_HEROES={

lion:{name:'شیر',emoji:'🦁',hp:130,speed:3.5,fireRate:15,damage:20,color:'#e6a817',

special:'غرش',specialCD:180,specialDesc:'دشمنان نزدیک میلرزند و کند میشوند'},

cheetah:{name:'یوزپلنگ',emoji:'🐆',hp:90,speed:6.2,fireRate:10,damage:14,color:'#e6b800',

special:'دوی سریع',specialCD:120,specialDesc:'سرعت ۲ برابر برای ۳ ثانیه'},

fox:{name:'روباه',emoji:'🦊',hp:100,speed:5.0,fireRate:9,damage:13,color:'#ff8844',

special:'فریب',specialCD:150,specialDesc:'دشمنان ۲ ثانیه گیج میشوند'},

turtle:{name:'لاکپشت',emoji:'🐢',hp:200,speed:2.0,fireRate:20,damage:25,color:'#66aa44',

special:'سپر لاکی',specialCD:200,specialDesc:'۳ ثانیه آسیب نمیبینی'},

monkey:{name:'میمون',emoji:'🐵',hp:95,speed:5.5,fireRate:8,damage:12,color:'#cc8844',

special:'موز پرتاب',specialCD:100,specialDesc:'پرتاب ۳ موز انفجاری'},

deer:{name:'گوزن',emoji:'🦌',hp:110,speed:4.8,fireRate:11,damage:16,color:'#bb7733',

special:'ضربه شاخ',specialCD:140,specialDesc:'پرتاب دشمنان نزدیک به عقب'},

eagle:{name:'عقاب',emoji:'🦅',hp:85,speed:5.8,fireRate:10,damage:18,color:'#ddcc88',

special:'پرواز',specialCD:160,specialDesc:'از روی موانع میپری'},

croc:{name:'تمساح',emoji:'🐊',hp:150,speed:3.0,fireRate:16,damage:28,color:'#558844',

special:'آرواره مرگ',specialCD:190,specialDesc:'گاز مرگبار به نزدیکترین دشمن'},

gorilla:{name:'گوریل',emoji:'🦍',hp:140,speed:3.8,fireRate:14,damage:22,color:'#776655',

special:'مشت زمین',specialCD:170,specialDesc:'ضربه به همه دشمنان اطراف'}

};

let selectedHero='lion';

let heroData=ALL_HEROES[selectedHero];

let specialCooldown=0;

function buildHeroCards(){

heroGrid='';

Object.entries(ALL_HEROES).forEach(([key,h])=>{

const card=document.createElement('div');

card.className='hero-card'+(key===selectedHero?' selected':'');

card=`<div class="hero-emoji">${h.emoji}</div><div>${h.name}</div>

<div class="hero-stats">❤️${h.hp} ⚡${h.speed} 💥${h.damage}<br>✨${h.special}</div>`;

card.addEventListener('click',()=>{

document.querySelectorAll('.hero-card').forEach(c=>c.classList.remove('selected'));

card.classList.add('selected');

selectedHero=key;

heroData=ALL_HEROES[key];

});

heroGrid(card);

});

}

buildHeroCards();

// Joystick handling

let joystick={dx:0,dy:0,active:false};

let joyId=null;

joyBase.addEventListener('touchstart',(e)=>{

e.preventDefault();joyId=e.changedTouches[0].identifier;joystick.active=true;

});

joyBase.addEventListener('touchmove',(e)=>{

e.preventDefault();

for(let t of e.changedTouches){

if(t.identifier===joyId){

const rect=joyBase.getBoundingClientRect();

const cx=rect.left+rect.width/2,cy=rect.top+rect.height/2;

let dx=t.clientX-cx,dy=t.clientY-cy;

const dist=Math.sqrt(dx*dx+dy*dy);

const maxDist=35;

if(dist>maxDist){dx=dx/dist*maxDist;dy=dy/dist*maxDist;}

joystick.dx=dx/maxDist;joystick.dy=dy/maxDist;

joyThumb.style.left=(25+dx)+'px';joyThumb.style.top=(25+dy)+'px';

}

}

});

joyBase.addEventListener('touchend',(e)=>{

for(let t of e.changedTouches){

if(t.identifier===joyId){joystick.active=false;joystick.dx=0;joystick.dy=0;

joyThumb.style.left='25px';joyThumb.style.top='25px';joyId=null;}

}

});

let shootDown=false;

btnShoot.addEventListener('touchstart',(e)=>{e.preventDefault();shootDown=true;});

btnShoot.addEventListener('touchend',()=>shootDown=false);

btnShoot.addEventListener('touchcancel',()=>shootDown=false);

btnSpecial.addEventListener('touchstart',(e)=>{

e.preventDefault();

if(specialCooldown<=0 && gameRunning && !gameOver) activateSpecial();

});

function activateSpecial(){

specialCooldown=heroData.specialCD;

const p=player;

switch(selectedHero){

case 'lion': // غرش - کند کردن دشمنان نزدیک

enemies.forEach(e=>{

const d=Math.hypot(e.x-p.x,e.y-p.y);

if(d<180){e.slowed=60;e.speed*=0.4;}

});

break;

case 'cheetah': // دوی سریع

p.speedBoost=60;p.speed*=2.2;

break;

case 'fox': // فریب - گیج کردن

enemies.forEach(e=>{

if(Math.hypot(e.x-p.x,e.y-p.y)<200)e.confused=60;

});

break;

case 'turtle': // سپر

p.shield=90;

break;

case 'monkey': // موز انفجاری

for(let i=0;i<3;i++){

setTimeout(()=>{

const t=enemies[Math.floor(Math.random()*enemies.length)];

if(t){t.hp-=25;if(t.hp<=0)killEnemy(t);}

},i*150);

}

break;

case 'deer': // پرتاب

enemies.forEach(e=>{

if(Math.hypot(e.x-p.x,e.y-p.y)<150){

const a=Math.atan2(e.y-p.y,e.x-p.x);

e.x+=Math.cos(a)*120;e.y+=Math.sin(a)*120;

e.hp-=15;if(e.hp<=0)killEnemy(e);

}

});

break;

case 'eagle': // پرش

p.zJump=30;p.zVel=-8;

break;

case 'croc':

const closest=enemies.reduce((a,b)=>Math.hypot(a.x-p.x,a.y-p.y)<Math.hypot(b.x-p.x,b.y-p.y)?a:b,enemies[0]);

if(closest&&Math.hypot(closest.x-p.x,closest.y-p.y)<130){closest.hp-=40;if(closest.hp<=0)killEnemy(closest);}

break;

case 'gorilla':

enemies.forEach(e=>{if(Math.hypot(e.x-p.x,e.y-p.y)<170){e.hp-=20;if(e.hp<=0)killEnemy(e);}});

break;

}

}

function initGame(){

heroData=ALL_HEROES[selectedHero];

player={

x:MAP_W/2,y:MAP_H/2,radius:18,

hp:heroData.hp,maxHp:heroData.hp,

speed:heroData.speed,fireRate:heroData.fireRate,

damage:heroData.damage,fireCooldown:0,

speedBoost:0,shield:0,zJump:0,zVel:0

};

enemies=[];bullets=[];enemyBullets=[];

score=0;kills=0;specialCooldown=0;

enemySpawnTimer=0;gameOver=false;gameRunning=true;

gameoverScreen.style.display='none';heroSelectDiv.style.display='none';

updateUI();

}

function spawnEnemy(){

const a=Math.random()*Math.PI*2,d=450+Math.random()*350;

let ex=player.x+Math.cos(a)*d,ey=player.y+Math.sin(a)*d;

ex=Math.max(40,Math.min(MAP_W-40,ex));

ey=Math.max(40,Math.min(MAP_H-40,ey));

const types=['gorilla','croc','fox_bot','deer_bot'];

const t=types[Math.floor(Math.random()*types.length)];

const stats={gorilla:{hp:70,sp:1.5,dmg:12,rad:18},croc:{hp:55,sp:2.2,dmg:9,rad:16},

fox_bot:{hp:45,sp:2.8,dmg:7,rad:15},deer_bot:{hp:50,sp:2.5,dmg:8,rad:17}};

enemies.push({

x:ex,y:ey,radius:stats[t].rad,hp:stats[t].hp,maxHp:stats[t].hp,

speed:stats[t].sp,damage:stats[t].dmg,type:t,fireCooldown:0,

slowed:0,confused:0

});

}

function killEnemy(e){

const idx=enemies.indexOf(e);

if(idx>-1)enemies.splice(idx,1);

kills++;score+=10;

}

function updateUI(){

scoreDisp.textContent=score;killDisp.textContent=kills;

hpFill.style.width=(player.hp/player.maxHp*100)+'%';

hpText.textContent=Math.ceil(player.hp);

specialDisp.textContent=specialCooldown>0?Math.ceil(specialCooldown/60)+'s':'⚡آماده';

}

function update(){

if(!gameRunning||gameOver)return;

// Player movement

let mx=joystick.dx*heroData.speed*(player.speedBoost>0?2.2:1);

let my=joystick.dy*heroData.speed*(player.speedBoost>0?2.2:1);

if(player.zJump>0){my-=4;player.zJump--;}

player.x=Math.max(20,Math.min(MAP_W-20,player.x+mx));

player.y=Math.max(20,Math.min(MAP_H-20,player.y+my));

if(player.speedBoost>0)player.speedBoost--;

if(player.shield>0)player.shield--;

if(specialCooldown>0)specialCooldown--;

// Auto-target nearest enemy for shooting

let nearestEnemy=null,nearestDist=250;

enemies.forEach(e=>{

const d=Math.hypot(e.x-player.x,e.y-player.y);

if(d<nearestDist){nearestDist=d;nearestEnemy=e;}

});

// Shooting

if(player.fireCooldown>0)player.fireCooldown--;

if(shootDown && player.fireCooldown<=0 && nearestEnemy){

const a=Math.atan2(nearestEnemy.y-player.y,nearestEnemy.x-player.x);

bullets.push({x:player.x,y:player.y,vx:Math.cos(a)*9,vy:Math.sin(a)*9,damage:heroData.damage});

player.fireCooldown=heroData.fireRate;

}

// Bullets

bullets.forEach(b=>{b.x+=b.vx;b.y+=b.vy;});

bullets=bullets.filter(b=>b.x>0&&b.x<MAP_W&&b.y>0&&b.y<MAP_H);

enemyBullets.forEach(b=>{b.x+=b.vx;b.y+=b.vy;});

enemyBullets=enemyBullets.filter(b=>b.x>0&&b.x<MAP_W&&b.y>0&&b.y<MAP_H);

// Bullet-enemy collision

bullets.forEach(b=>{

enemies.forEach(e=>{

if(Math.hypot(b.x-e.x,b.y-e.y)<e.radius+5){

e.hp-=b.damage;b.hit=true;

if(e.hp<=0)killEnemy(e);

}

});

});

bullets=bullets.filter(b=>!b.hit);

// Enemy bullet-player collision

enemyBullets.forEach(b=>{

if(Math.hypot(b.x-player.x,b.y-player.y)<player.radius+5){

if(player.shield<=0)player.hp-=b.damage||8;

b.hit=true;

}

});

enemyBullets=enemyBullets.filter(b=>!b.hit);

// Enemy AI

enemies.forEach(e=>{

if(e.slowed>0){e.slowed--;if(e.slowed===0)e.speed*=2.5;}

if(e.confused>0){e.confused--;return;}

const dx=player.x-e.x,dy=player.y-e.y,dist=Math.hypot(dx,dy);

if(dist>5){e.x+=dx/dist*e.speed;e.y+=dy/dist*e.speed;}

if(e.fireCooldown>0)e.fireCooldown--;

if(dist<300 && e.fireCooldown<=0 && Math.random()<0.02){

const a=Math.atan2(player.y-e.y,player.x-e.x);

enemyBullets.push({x:e.x,y:e.y,vx:Math.cos(a)*7,vy:Math.sin(a)*7,damage:e.damage});

e.fireCooldown=25;

}

});

// Spawn

enemySpawnTimer--;

if(enemySpawnTimer<=0 && enemies.length<12){

spawnEnemy();enemySpawnTimer=70+Math.random()*50;

}

if(player.hp<=0){gameOver=true;gameRunning=false;gameoverScreen.style.display='flex';

finalScoreSpan.textContent='⭐ '+score+' 💀 '+kills;}

updateUI();

}

function draw(){

ctx.clearRect(0,0,W,H);

const camX=player.x-W/2,camY=player.y-H/2;

ctx.save();ctx.translate(-camX,-camY);

// Grass bg

ctx.fillStyle='#4a8c3f';ctx.fillRect(0,0,MAP_W,MAP_H);

// Grid

ctx.strokeStyle='#3a7030';ctx.lineWidth=1;

for(let i=0;i<MAP_W;i+=80){ctx.beginPath();ctx.moveTo(i,0);ctx.lineTo(i,MAP_H);ctx.stroke();}

for(let i=0;i<MAP_H;i

gt lt
۰
۰
محمد حسین صادقی زاده
محمد حسین صادقی زاده
شاید از این پست‌ها خوشتان بیاید