# Δημιουργία ενός Διαστημικού Παιχνιδιού Μέρος 2: Σχεδίαση Ήρωα και Τεράτων στον Καμβά ## Κουίζ πριν το μάθημα [Κουίζ πριν το μάθημα](https://ff-quizzes.netlify.app/web/quiz/31) ## Ο Καμβάς Ο καμβάς είναι ένα στοιχείο HTML που από προεπιλογή δεν έχει περιεχόμενο· είναι ένας λευκός καμβάς. Πρέπει να προσθέσετε περιεχόμενο σχεδιάζοντας πάνω του. ✅ Διαβάστε [περισσότερα για το Canvas API](https://developer.mozilla.org/docs/Web/API/Canvas_API) στο MDN. Δείτε πώς δηλώνεται συνήθως, ως μέρος του σώματος της σελίδας: ```html ``` Στο παραπάνω παράδειγμα ορίζουμε τα `id`, `width` και `height`. - `id`: το ορίζετε για να μπορείτε να αποκτήσετε αναφορά όταν χρειαστεί να αλληλεπιδράσετε με αυτό. - `width`: αυτό είναι το πλάτος του στοιχείου. - `height`: αυτό είναι το ύψος του στοιχείου. ## Σχεδίαση απλών γεωμετρικών σχημάτων Ο καμβάς χρησιμοποιεί ένα καρτεσιανό σύστημα συντεταγμένων για να σχεδιάζει αντικείμενα. Έτσι, χρησιμοποιεί άξονες x και y για να εκφράσει τη θέση ενός αντικειμένου. Η θέση `0,0` είναι η πάνω αριστερή γωνία και η κάτω δεξιά είναι αυτή που ορίσατε ως ΠΛΑΤΟΣ (WIDTH) και ΥΨΟΣ (HEIGHT) του καμβά. ![το πλέγμα του καμβά](../../../../translated_images/canvas_grid.5f209da785ded492a01ece440e3032afe51efa500cc2308e5ea4252487ceaf0b.el.png) > Εικόνα από [MDN](https://developer.mozilla.org/docs/Web/API/Canvas_API/Tutorial/Drawing_shapes) Για να σχεδιάσετε στον καμβά, πρέπει να ακολουθήσετε τα εξής βήματα: 1. **Αποκτήστε αναφορά** στο στοιχείο του καμβά. 2. **Αποκτήστε αναφορά** στο στοιχείο Context που βρίσκεται πάνω στον καμβά. 3. **Εκτελέστε μια λειτουργία σχεδίασης** χρησιμοποιώντας το στοιχείο context. Ο κώδικας για τα παραπάνω βήματα συνήθως μοιάζει κάπως έτσι: ```javascript // draws a red rectangle //1. get the canvas reference canvas = document.getElementById("myCanvas"); //2. set the context to 2D to draw basic shapes ctx = canvas.getContext("2d"); //3. fill it with the color red ctx.fillStyle = 'red'; //4. and draw a rectangle with these parameters, setting location and size ctx.fillRect(0,0, 200, 200) // x,y,width, height ``` ✅ Το Canvas API επικεντρώνεται κυρίως σε δισδιάστατα σχήματα, αλλά μπορείτε επίσης να σχεδιάσετε τρισδιάστατα αντικείμενα σε μια ιστοσελίδα· για αυτό, μπορείτε να χρησιμοποιήσετε το [WebGL API](https://developer.mozilla.org/docs/Web/API/WebGL_API). Μπορείτε να σχεδιάσετε διάφορα πράγματα με το Canvas API, όπως: - **Γεωμετρικά σχήματα**, έχουμε ήδη δείξει πώς να σχεδιάσετε ένα ορθογώνιο, αλλά μπορείτε να σχεδιάσετε πολλά περισσότερα. - **Κείμενο**, μπορείτε να σχεδιάσετε κείμενο με οποιαδήποτε γραμματοσειρά και χρώμα επιθυμείτε. - **Εικόνες**, μπορείτε να σχεδιάσετε μια εικόνα βασισμένη σε ένα αρχείο εικόνας, όπως .jpg ή .png. ✅ Δοκιμάστε το! Ξέρετε πώς να σχεδιάσετε ένα ορθογώνιο, μπορείτε να σχεδιάσετε έναν κύκλο σε μια σελίδα; Ρίξτε μια ματιά σε μερικά ενδιαφέροντα σχέδια στον καμβά στο CodePen. Δείτε ένα [ιδιαίτερα εντυπωσιακό παράδειγμα](https://codepen.io/dissimulate/pen/KrAwx). ## Φόρτωση και σχεδίαση ενός αρχείου εικόνας Μπορείτε να φορτώσετε ένα αρχείο εικόνας δημιουργώντας ένα αντικείμενο `Image` και ορίζοντας την ιδιότητα `src`. Στη συνέχεια, ακούτε το γεγονός `load` για να γνωρίζετε πότε είναι έτοιμο για χρήση. Ο κώδικας μοιάζει κάπως έτσι: ### Φόρτωση αρχείου ```javascript const img = new Image(); img.src = 'path/to/my/image.png'; img.onload = () => { // image loaded and ready to be used } ``` ### Πρότυπο φόρτωσης αρχείου Συνιστάται να τυλίξετε τα παραπάνω σε μια κατασκευή όπως η παρακάτω, ώστε να είναι πιο εύχρηστο και να προσπαθείτε να το χειριστείτε μόνο όταν φορτωθεί πλήρως: ```javascript function loadAsset(path) { return new Promise((resolve) => { const img = new Image(); img.src = path; img.onload = () => { // image loaded and ready to be used resolve(img); } }) } // use like so async function run() { const heroImg = await loadAsset('hero.png') const monsterImg = await loadAsset('monster.png') } ``` Για να σχεδιάσετε στοιχεία του παιχνιδιού στην οθόνη, ο κώδικάς σας θα μοιάζει κάπως έτσι: ```javascript async function run() { const heroImg = await loadAsset('hero.png') const monsterImg = await loadAsset('monster.png') canvas = document.getElementById("myCanvas"); ctx = canvas.getContext("2d"); ctx.drawImage(heroImg, canvas.width/2,canvas.height/2); ctx.drawImage(monsterImg, 0,0); } ``` ## Ώρα να ξεκινήσετε να δημιουργείτε το παιχνίδι σας ### Τι να δημιουργήσετε Θα δημιουργήσετε μια ιστοσελίδα με ένα στοιχείο καμβά. Θα πρέπει να εμφανίζει μια μαύρη οθόνη `1024*768`. Σας παρέχουμε δύο εικόνες: - Διαστημόπλοιο Ήρωα ![Διαστημόπλοιο Ήρωα](../../../../translated_images/player.dd24c1afa8c71e9b82b2958946d4bad13308681392d4b5ddcc61a0e818ef8088.el.png) - 5*5 τέρατα ![Διαστημόπλοιο Τέρατος](../../../../translated_images/enemyShip.5df2a822c16650c2fb3c06652e8ec8120cdb9122a6de46b9a1a56d54db22657f.el.png) ### Προτεινόμενα βήματα για να ξεκινήσετε την ανάπτυξη Βρείτε τα αρχεία που έχουν δημιουργηθεί για εσάς στον υποφάκελο `your-work`. Θα πρέπει να περιέχει τα εξής: ```bash -| assets -| enemyShip.png -| player.png -| index.html -| app.js -| package.json ``` Ανοίξτε το αντίγραφο αυτού του φακέλου στο Visual Studio Code. Πρέπει να έχετε ρυθμίσει ένα τοπικό περιβάλλον ανάπτυξης, κατά προτίμηση με το Visual Studio Code, το NPM και το Node εγκατεστημένα. Αν δεν έχετε ρυθμίσει το `npm` στον υπολογιστή σας, [δείτε πώς να το κάνετε](https://www.npmjs.com/get-npm). Ξεκινήστε το έργο σας πλοηγούμενοι στον φάκελο `your_work`: ```bash cd your-work npm start ``` Το παραπάνω θα ξεκινήσει έναν HTTP Server στη διεύθυνση `http://localhost:5000`. Ανοίξτε έναν περιηγητή και εισάγετε αυτή τη διεύθυνση. Αυτή τη στιγμή είναι μια κενή σελίδα, αλλά αυτό θα αλλάξει. > Σημείωση: για να δείτε αλλαγές στην οθόνη σας, ανανεώστε τον περιηγητή σας. ### Προσθήκη κώδικα Προσθέστε τον απαραίτητο κώδικα στο `your-work/app.js` για να λύσετε τα παρακάτω: 1. **Σχεδιάστε** έναν καμβά με μαύρο φόντο > συμβουλή: προσθέστε δύο γραμμές κάτω από το κατάλληλο TODO στο `/app.js`, ορίζοντας το στοιχείο `ctx` να είναι μαύρο και τις συντεταγμένες πάνω/αριστερά στο 0,0 και το ύψος και το πλάτος να είναι ίσα με αυτά του καμβά. 2. **Φορτώστε** υφές > συμβουλή: προσθέστε τις εικόνες του παίκτη και του εχθρού χρησιμοποιώντας `await loadTexture` και περνώντας τη διαδρομή της εικόνας. Δεν θα τις δείτε ακόμα στην οθόνη! 3. **Σχεδιάστε** τον ήρωα στο κέντρο της οθόνης στο κάτω μισό > συμβουλή: χρησιμοποιήστε το API `drawImage` για να σχεδιάσετε το heroImg στην οθόνη, ορίζοντας `canvas.width / 2 - 45` και `canvas.height - canvas.height / 4)`. 4. **Σχεδιάστε** 5*5 τέρατα > συμβουλή: Τώρα μπορείτε να αποσχολιάσετε τον κώδικα για να σχεδιάσετε τους εχθρούς στην οθόνη. Στη συνέχεια, πηγαίνετε στη συνάρτηση `createEnemies` και ολοκληρώστε την. Αρχικά, ορίστε μερικές σταθερές: ```javascript const MONSTER_TOTAL = 5; const MONSTER_WIDTH = MONSTER_TOTAL * 98; const START_X = (canvas.width - MONSTER_WIDTH) / 2; const STOP_X = START_X + MONSTER_WIDTH; ``` έπειτα, δημιουργήστε έναν βρόχο για να σχεδιάσετε τον πίνακα των τεράτων στην οθόνη: ```javascript for (let x = START_X; x < STOP_X; x += 98) { for (let y = 0; y < 50 * 5; y += 50) { ctx.drawImage(enemyImg, x, y); } } ``` ## Αποτέλεσμα Το τελικό αποτέλεσμα θα πρέπει να μοιάζει κάπως έτσι: ![Μαύρη οθόνη με έναν ήρωα και 5*5 τέρατα](../../../../translated_images/partI-solution.36c53b48c9ffae2a5e15496b23b604ba5393433e4bf91608a7a0a020eb7a2691.el.png) ## Λύση Προσπαθήστε να το λύσετε μόνοι σας πρώτα, αλλά αν κολλήσετε, ρίξτε μια ματιά σε μια [λύση](../../../../6-space-game/2-drawing-to-canvas/solution/app.js). --- ## 🚀 Πρόκληση Μάθατε για τη σχεδίαση με το Canvas API που επικεντρώνεται σε 2D· ρίξτε μια ματιά στο [WebGL API](https://developer.mozilla.org/docs/Web/API/WebGL_API) και προσπαθήστε να σχεδιάσετε ένα τρισδιάστατο αντικείμενο. ## Κουίζ μετά το μάθημα [Κουίζ μετά το μάθημα](https://ff-quizzes.netlify.app/web/quiz/32) ## Ανασκόπηση & Αυτομελέτη Μάθετε περισσότερα για το Canvas API [διαβάζοντας σχετικά](https://developer.mozilla.org/docs/Web/API/Canvas_API). ## Εργασία [Παίξτε με το Canvas API](assignment.md) --- **Αποποίηση ευθύνης**: Αυτό το έγγραφο έχει μεταφραστεί χρησιμοποιώντας την υπηρεσία αυτόματης μετάφρασης [Co-op Translator](https://github.com/Azure/co-op-translator). Παρόλο που καταβάλλουμε προσπάθειες για ακρίβεια, παρακαλούμε να έχετε υπόψη ότι οι αυτοματοποιημένες μεταφράσεις ενδέχεται να περιέχουν λάθη ή ανακρίβειες. Το πρωτότυπο έγγραφο στη μητρική του γλώσσα θα πρέπει να θεωρείται η αυθεντική πηγή. Για κρίσιμες πληροφορίες, συνιστάται επαγγελματική ανθρώπινη μετάφραση. Δεν φέρουμε ευθύνη για τυχόν παρεξηγήσεις ή εσφαλμένες ερμηνείες που προκύπτουν από τη χρήση αυτής της μετάφρασης.