You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
311 lines
20 KiB
311 lines
20 KiB
<!--
|
|
CO_OP_TRANSLATOR_METADATA:
|
|
{
|
|
"original_hash": "a6ce295ff03bb49df7a3e17e6e7100a0",
|
|
"translation_date": "2025-08-28T16:36:25+00:00",
|
|
"source_file": "6-space-game/4-collision-detection/README.md",
|
|
"language_code": "ne"
|
|
}
|
|
-->
|
|
# स्पेस गेम बनाउनुहोस् भाग ४: लेजर थप्ने र टक्कर पत्ता लगाउने
|
|
|
|
## प्रि-लेक्चर क्विज
|
|
|
|
[प्रि-लेक्चर क्विज](https://ff-quizzes.netlify.app/web/quiz/35)
|
|
|
|
यस पाठमा तपाईंले JavaScript प्रयोग गरेर लेजर कसरी चलाउने भन्ने सिक्नुहुनेछ! हामी हाम्रो खेलमा दुईवटा कुरा थप्नेछौं:
|
|
|
|
- **लेजर**: यो लेजर तपाईंको नायकको जहाजबाट माथि तिर चल्छ।
|
|
- **टक्कर पत्ता लगाउने प्रणाली**: *शूट* गर्ने क्षमता कार्यान्वयनको भागको रूपमा, हामी केही रमाइलो खेल नियमहरू पनि थप्नेछौं:
|
|
- **लेजरले दुश्मनलाई हान्छ**: लेजरले हानेमा दुश्मन मर्छ।
|
|
- **लेजरले स्क्रिनको माथिल्लो भागलाई हान्छ**: स्क्रिनको माथिल्लो भागमा ठोक्किएमा लेजर नष्ट हुन्छ।
|
|
- **दुश्मन र नायकको टक्कर**: दुश्मन र नायक एकअर्कामा ठोक्किएमा दुबै नष्ट हुन्छन्।
|
|
- **दुश्मनले स्क्रिनको तल्लो भागलाई हान्छ**: दुश्मनले स्क्रिनको तल्लो भागमा ठोक्किएमा दुश्मन र नायक दुबै नष्ट हुन्छन्।
|
|
|
|
संक्षेपमा, तपाईं -- *नायक* -- ले दुश्मनहरूलाई स्क्रिनको तल्लो भागमा पुग्नुअघि लेजरले हान्नुपर्छ।
|
|
|
|
✅ पहिलो पटक लेखिएको कम्प्युटर गेमको बारेमा थोरै अनुसन्धान गर्नुहोस्। यसको कार्यक्षमता के थियो?
|
|
|
|
आउनुहोस्, नायक बन्ने प्रयास गरौं!
|
|
|
|
## टक्कर पत्ता लगाउने प्रणाली
|
|
|
|
टक्कर पत्ता लगाउने प्रणाली कसरी गर्ने? हामीले हाम्रो खेलका वस्तुहरूलाई आयताकारको रूपमा सोच्नुपर्छ। किनभने खेल वस्तुहरूलाई चित्रण गर्न प्रयोग गरिने छवि आयताकार हुन्छ: यसमा `x`, `y`, `width` र `height` हुन्छ।
|
|
|
|
यदि दुईवटा आयताकारहरू, जस्तै नायक र दुश्मन, *अन्तरसेक्ट* गर्छन् भने, टक्कर हुन्छ। त्यसपछि के हुनुपर्छ भन्ने कुरा खेलका नियमहरूमा निर्भर गर्दछ। टक्कर पत्ता लगाउन निम्न कुरा आवश्यक पर्छ:
|
|
|
|
1. खेल वस्तुको आयताकार प्रतिनिधित्व प्राप्त गर्ने तरिका, जस्तै:
|
|
|
|
```javascript
|
|
rectFromGameObject() {
|
|
return {
|
|
top: this.y,
|
|
left: this.x,
|
|
bottom: this.y + this.height,
|
|
right: this.x + this.width
|
|
}
|
|
}
|
|
```
|
|
|
|
2. तुलना गर्ने कार्य, यो कार्य यसरी देखिन सक्छ:
|
|
|
|
```javascript
|
|
function intersectRect(r1, r2) {
|
|
return !(r2.left > r1.right ||
|
|
r2.right < r1.left ||
|
|
r2.top > r1.bottom ||
|
|
r2.bottom < r1.top);
|
|
}
|
|
```
|
|
|
|
## वस्तुहरू कसरी नष्ट गर्ने
|
|
|
|
खेलमा वस्तुहरू नष्ट गर्न, खेललाई यो वस्तु अब पेन्ट गर्न नहुने जानकारी दिनुपर्छ। यसको एउटा तरिका भनेको कुनै घटना हुँदा खेल वस्तुलाई *मरेको* भनेर चिन्ह लगाउनु हो, जस्तै:
|
|
|
|
```javascript
|
|
// collision happened
|
|
enemy.dead = true
|
|
```
|
|
|
|
त्यसपछि तपाईंले *मरेका* वस्तुहरूलाई स्क्रिन पुनः पेन्ट गर्नु अघि हटाउन सक्नुहुन्छ, जस्तै:
|
|
|
|
```javascript
|
|
gameObjects = gameObject.filter(go => !go.dead);
|
|
```
|
|
|
|
## लेजर कसरी चलाउने
|
|
|
|
लेजर चलाउनु भनेको कुञ्जी-घटना (key-event) मा प्रतिक्रिया जनाउनु र एउटा वस्तु सिर्जना गर्नु हो, जुन निश्चित दिशामा सर्छ। त्यसैले हामीले निम्न चरणहरू पूरा गर्नुपर्छ:
|
|
|
|
1. **लेजर वस्तु सिर्जना गर्नुहोस्**: नायकको जहाजको माथिबाट, जसले सिर्जना भएलगत्तै स्क्रिनको माथि तिर सर्छ।
|
|
2. **कुञ्जी-घटनामा कोड जोड्नुहोस्**: हामीले किबोर्डको एउटा कुञ्जी चयन गर्नुपर्छ, जसले खेलाडीले लेजर चलाएको प्रतिनिधित्व गर्छ।
|
|
3. **लेजर जस्तो देखिने खेल वस्तु सिर्जना गर्नुहोस्**: जब कुञ्जी थिचिन्छ।
|
|
|
|
## लेजरमा कूलडाउन
|
|
|
|
लेजरले प्रत्येक पटक कुञ्जी थिच्दा चल्नुपर्छ, जस्तै *स्पेस* कुञ्जी। तर, खेलले धेरै छोटो समयमा धेरै लेजर उत्पादन नगरोस् भनेर हामीले यसलाई समाधान गर्नुपर्छ। समाधान भनेको *कूलडाउन* नामक टाइमर कार्यान्वयन गर्नु हो, जसले लेजरलाई निश्चित समयपछि मात्र चल्न दिन्छ। तपाईं यसलाई निम्न तरिकाले कार्यान्वयन गर्न सक्नुहुन्छ:
|
|
|
|
```javascript
|
|
class Cooldown {
|
|
constructor(time) {
|
|
this.cool = false;
|
|
setTimeout(() => {
|
|
this.cool = true;
|
|
}, time)
|
|
}
|
|
}
|
|
|
|
class Weapon {
|
|
constructor {
|
|
}
|
|
fire() {
|
|
if (!this.cooldown || this.cooldown.cool) {
|
|
// produce a laser
|
|
this.cooldown = new Cooldown(500);
|
|
} else {
|
|
// do nothing - it hasn't cooled down yet.
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
✅ स्पेस गेम श्रृंखलाको पहिलो पाठमा *कूलडाउन* को बारेमा सम्झनुहोस्।
|
|
|
|
## के निर्माण गर्ने
|
|
|
|
तपाईंले अघिल्लो पाठबाट रहेको कोड (जसलाई तपाईंले सफा र पुनः संरचित गर्नुभएको हुनुपर्छ) लिनेछ र यसलाई विस्तार गर्नुहुनेछ। भाग II बाट कोड सुरु गर्नुहोस् वा [भाग III-स्टार्टर](../../../../../../../../../your-work) मा रहेको कोड प्रयोग गर्नुहोस्।
|
|
|
|
> सुझाव: तपाईंले काम गर्ने लेजर पहिले नै तपाईंको *assets* फोल्डरमा छ र तपाईंको कोडले यसलाई सन्दर्भित गरिरहेको छ।
|
|
|
|
- **टक्कर पत्ता लगाउने प्रणाली थप्नुहोस्**, जब लेजरले केही ठोक्किन्छ, निम्न नियमहरू लागू हुनुपर्छ:
|
|
1. **लेजरले दुश्मनलाई हान्छ**: लेजरले हानेमा दुश्मन मर्छ।
|
|
2. **लेजरले स्क्रिनको माथिल्लो भागलाई हान्छ**: लेजर स्क्रिनको माथिल्लो भागमा ठोक्किएमा नष्ट हुन्छ।
|
|
3. **दुश्मन र नायकको टक्कर**: दुश्मन र नायक एकअर्कामा ठोक्किएमा दुबै नष्ट हुन्छन्।
|
|
4. **दुश्मनले स्क्रिनको तल्लो भागलाई हान्छ**: दुश्मनले स्क्रिनको तल्लो भागमा ठोक्किएमा दुश्मन र नायक दुबै नष्ट हुन्छन्।
|
|
|
|
## सिफारिस गरिएका चरणहरू
|
|
|
|
`your-work` सब फोल्डरमा तपाईंका लागि सिर्जना गरिएका फाइलहरू खोज्नुहोस्। यसमा निम्न समावेश हुनुपर्छ:
|
|
|
|
```bash
|
|
-| assets
|
|
-| enemyShip.png
|
|
-| player.png
|
|
-| laserRed.png
|
|
-| index.html
|
|
-| app.js
|
|
-| package.json
|
|
```
|
|
|
|
तपाईं आफ्नो प्रोजेक्ट `your_work` फोल्डरबाट निम्न टाइप गरेर सुरु गर्नुहोस्:
|
|
|
|
```bash
|
|
cd your-work
|
|
npm start
|
|
```
|
|
|
|
माथिको कमाण्डले `http://localhost:5000` मा HTTP सर्भर सुरु गर्नेछ। ब्राउजर खोल्नुहोस् र उक्त ठेगाना प्रविष्ट गर्नुहोस्, अहिले यो नायक र सबै दुश्मनहरू देखाउनेछ, तर केही चलिरहेको छैन - अहिलेसम्म :).
|
|
|
|
### कोड थप्नुहोस्
|
|
|
|
1. **आयताकार प्रतिनिधित्व सेटअप गर्नुहोस्, टक्कर पत्ता लगाउनको लागि**। तलको कोडले `GameObject` को आयताकार प्रतिनिधित्व प्राप्त गर्न अनुमति दिन्छ। आफ्नो `GameObject` कक्षालाई यसरी विस्तार गर्नुहोस्:
|
|
|
|
```javascript
|
|
rectFromGameObject() {
|
|
return {
|
|
top: this.y,
|
|
left: this.x,
|
|
bottom: this.y + this.height,
|
|
right: this.x + this.width,
|
|
};
|
|
}
|
|
```
|
|
|
|
2. **टक्कर जाँच गर्ने कोड थप्नुहोस्**। यो नयाँ कार्य हुनेछ, जसले दुई आयताकारहरू अन्तरसेक्ट भए/नभएको परीक्षण गर्छ:
|
|
|
|
```javascript
|
|
function intersectRect(r1, r2) {
|
|
return !(
|
|
r2.left > r1.right ||
|
|
r2.right < r1.left ||
|
|
r2.top > r1.bottom ||
|
|
r2.bottom < r1.top
|
|
);
|
|
}
|
|
```
|
|
|
|
3. **लेजर चलाउने क्षमता थप्नुहोस्**
|
|
1. **कुञ्जी-घटना सन्देश थप्नुहोस्**। *स्पेस* कुञ्जीले नायकको जहाजको माथि लेजर सिर्जना गर्नुपर्छ। `Messages` वस्तुमा तीनवटा स्थिरांक थप्नुहोस्:
|
|
|
|
```javascript
|
|
KEY_EVENT_SPACE: "KEY_EVENT_SPACE",
|
|
COLLISION_ENEMY_LASER: "COLLISION_ENEMY_LASER",
|
|
COLLISION_ENEMY_HERO: "COLLISION_ENEMY_HERO",
|
|
```
|
|
|
|
1. **स्पेस कुञ्जी ह्यान्डल गर्नुहोस्**। `window.addEventListener` को `keyup` कार्यलाई सम्पादन गरेर स्पेस कुञ्जीलाई ह्यान्डल गर्नुहोस्:
|
|
|
|
```javascript
|
|
} else if(evt.keyCode === 32) {
|
|
eventEmitter.emit(Messages.KEY_EVENT_SPACE);
|
|
}
|
|
```
|
|
|
|
1. **स्रोतहरू थप्नुहोस्**। `initGame()` कार्यलाई सम्पादन गरेर नायकले स्पेस बार थिच्दा लेजर चलाउन सक्ने सुनिश्चित गर्नुहोस्:
|
|
|
|
```javascript
|
|
eventEmitter.on(Messages.KEY_EVENT_SPACE, () => {
|
|
if (hero.canFire()) {
|
|
hero.fire();
|
|
}
|
|
```
|
|
|
|
र नयाँ `eventEmitter.on()` कार्य थप्नुहोस्, जसले दुश्मन र लेजर ठोक्किँदा व्यवहार सुनिश्चित गर्छ:
|
|
|
|
```javascript
|
|
eventEmitter.on(Messages.COLLISION_ENEMY_LASER, (_, { first, second }) => {
|
|
first.dead = true;
|
|
second.dead = true;
|
|
})
|
|
```
|
|
|
|
1. **वस्तु चलाउनुहोस्**, लेजरलाई स्क्रिनको माथि तिर क्रमशः सर्ने सुनिश्चित गर्नुहोस्। तपाईंले नयाँ `Laser` कक्षा सिर्जना गर्नुहुनेछ, जसले `GameObject` लाई विस्तार गर्छ, जस्तै:
|
|
|
|
```javascript
|
|
class Laser extends GameObject {
|
|
constructor(x, y) {
|
|
super(x,y);
|
|
(this.width = 9), (this.height = 33);
|
|
this.type = 'Laser';
|
|
this.img = laserImg;
|
|
let id = setInterval(() => {
|
|
if (this.y > 0) {
|
|
this.y -= 15;
|
|
} else {
|
|
this.dead = true;
|
|
clearInterval(id);
|
|
}
|
|
}, 100)
|
|
}
|
|
}
|
|
```
|
|
|
|
1. **टक्कर ह्यान्डल गर्नुहोस्**, लेजरका लागि टक्कर नियम कार्यान्वयन गर्नुहोस्। `updateGameObjects()` कार्य थप्नुहोस्, जसले ठोक्किएका वस्तुहरूको परीक्षण गर्छ:
|
|
|
|
```javascript
|
|
function updateGameObjects() {
|
|
const enemies = gameObjects.filter(go => go.type === 'Enemy');
|
|
const lasers = gameObjects.filter((go) => go.type === "Laser");
|
|
// laser hit something
|
|
lasers.forEach((l) => {
|
|
enemies.forEach((m) => {
|
|
if (intersectRect(l.rectFromGameObject(), m.rectFromGameObject())) {
|
|
eventEmitter.emit(Messages.COLLISION_ENEMY_LASER, {
|
|
first: l,
|
|
second: m,
|
|
});
|
|
}
|
|
});
|
|
});
|
|
|
|
gameObjects = gameObjects.filter(go => !go.dead);
|
|
}
|
|
```
|
|
|
|
सुनिश्चित गर्नुहोस् कि `updateGameObjects()` लाई तपाईंको खेल लूपमा `window.onload` मा थपिएको छ।
|
|
|
|
4. **लेजरमा कूलडाउन कार्यान्वयन गर्नुहोस्**, ताकि यो निश्चित समयपछि मात्र चल्न सकोस्।
|
|
|
|
अन्तमा, `Hero` कक्षालाई सम्पादन गरेर यसलाई कूलडाउन गर्न सक्षम बनाउनुहोस्:
|
|
|
|
```javascript
|
|
class Hero extends GameObject {
|
|
constructor(x, y) {
|
|
super(x, y);
|
|
(this.width = 99), (this.height = 75);
|
|
this.type = "Hero";
|
|
this.speed = { x: 0, y: 0 };
|
|
this.cooldown = 0;
|
|
}
|
|
fire() {
|
|
gameObjects.push(new Laser(this.x + 45, this.y - 10));
|
|
this.cooldown = 500;
|
|
|
|
let id = setInterval(() => {
|
|
if (this.cooldown > 0) {
|
|
this.cooldown -= 100;
|
|
} else {
|
|
clearInterval(id);
|
|
}
|
|
}, 200);
|
|
}
|
|
canFire() {
|
|
return this.cooldown === 0;
|
|
}
|
|
}
|
|
```
|
|
|
|
यस बिन्दुमा, तपाईंको खेलमा केही कार्यक्षमता हुनेछ! तपाईंले आफ्नो एरो कुञ्जीहरू प्रयोग गरेर नेभिगेट गर्न सक्नुहुन्छ, स्पेस बारले लेजर चलाउन सक्नुहुन्छ, र लेजरले दुश्मनलाई हानेमा दुश्मन हराउँछ। राम्रो काम!
|
|
|
|
---
|
|
|
|
## 🚀 चुनौती
|
|
|
|
विस्फोट थप्नुहोस्! [Space Art repo](../../../../6-space-game/solution/spaceArt/readme.txt) मा खेलका सम्पत्तिहरू हेर्नुहोस् र लेजरले एलियनलाई हानेमा विस्फोट थप्ने प्रयास गर्नुहोस्।
|
|
|
|
## पोस्ट-लेक्चर क्विज
|
|
|
|
[पोस्ट-लेक्चर क्विज](https://ff-quizzes.netlify.app/web/quiz/36)
|
|
|
|
## समीक्षा र आत्म-अध्ययन
|
|
|
|
तपाईंको खेलमा अहिलेसम्म भएका इन्टरभलहरूसँग प्रयोग गर्नुहोस्। जब तपाईंले तिनीहरूलाई परिवर्तन गर्नुहुन्छ, के हुन्छ? [JavaScript टाइमिङ इभेन्ट्स](https://www.freecodecamp.org/news/javascript-timing-events-settimeout-and-setinterval/) को बारेमा थप पढ्नुहोस्।
|
|
|
|
## असाइनमेन्ट
|
|
|
|
[टक्करहरूको अन्वेषण गर्नुहोस्](assignment.md)
|
|
|
|
---
|
|
|
|
**अस्वीकरण**:
|
|
यो दस्तावेज़ AI अनुवाद सेवा [Co-op Translator](https://github.com/Azure/co-op-translator) प्रयोग गरेर अनुवाद गरिएको छ। हामी शुद्धताको लागि प्रयास गर्छौं, तर कृपया ध्यान दिनुहोस् कि स्वचालित अनुवादमा त्रुटिहरू वा अशुद्धताहरू हुन सक्छ। यसको मूल भाषा मा रहेको मूल दस्तावेज़लाई आधिकारिक स्रोत मानिनुपर्छ। महत्वपूर्ण जानकारीको लागि, व्यावसायिक मानव अनुवाद सिफारिस गरिन्छ। यस अनुवादको प्रयोगबाट उत्पन्न हुने कुनै पनि गलतफहमी वा गलत व्याख्याको लागि हामी जिम्मेवार हुने छैनौं। |