การจัดการรายการเอนทิตีประเภทต่าง ๆ - มีวิธีที่ดีกว่านี้ไหม?


9

ฉันกำลังพัฒนาเกมอวกาศ 2 มิติสำหรับอุปกรณ์พกพา แต่มันซับซ้อนจริง ๆ และโซลูชันของฉันสับสนจริง ๆ และสร้างเซ็กเมนต์รหัสซ้ำจำนวนมาก

ฉันได้ระดับโลกที่ฉันมีรายการหลากหลายของวัตถุที่แตกต่างกันเช่น:

List<Enemy> enemys;
List<Projectile> projectiles;
List<Collectable> collectables;
List<Asteroid> asteroids;
List<Effect> effects;
..

แต่ละรายการได้รับการปรับปรุงโดยระดับโลก แต่นั่นไม่ใช่ทั้งหมด .. ศัตรูแต่ละคนมีรายชื่อเครื่องยนต์และรายชื่ออาวุธที่ได้รับการปรับปรุงโดยศัตรู ตอนนี้แต่ละเครื่องยนต์เพิ่มเอฟเฟกต์ไฟบางส่วนให้กับรายการ 'เอฟเฟกต์โลก' และอาวุธแต่ละอันจะเพิ่มโปรเจ็คเตอร์ลงใน 'โปรเจ็คเตอร์' ของรายการโลก คลาสทั้งหมดเหล่านี้มีพารามิเตอร์ที่แตกต่างกันดังนั้นฉันต้องการการปรับปรุงพิเศษและฟังก์ชั่นการแสดงผลเพิ่มเติมสำหรับแต่ละชั้นเรียน

อย่างน้อยพวกเขาก็เป็นเด็กทั้งหมดของ 'GameObject' ซึ่งให้สิ่งพื้นฐานเช่นตำแหน่งความเร็วและเวกเตอร์การเร่งความเร็ว

มีวิธีที่ดีกว่าหรือมากกว่าทั่วไปในการทำเช่นนี้? เหมือนคลาส catch-all หนึ่งคลาสที่มีพารามิเตอร์และวิธีการที่เป็นไปได้ทั้งหมดสำหรับวัตถุที่แตกต่างกันทั้งหมด (ฉันคิดว่านี่จะสร้างรหัสที่สับสนมากขึ้น)


นี้คล้ายกับคำถามของฉัน: gamedev.stackexchange.com/questions/22559/…ฉันขอแนะนำให้ดูคำตอบที่ได้รับ
Derek

คำตอบ:


5

มีวิธีที่ดีกว่าหรือมากกว่าทั่วไปในการทำเช่นนี้? เหมือนคลาส catch-all หนึ่งคลาสที่มีพารามิเตอร์และวิธีการที่เป็นไปได้ทั้งหมดสำหรับวัตถุที่แตกต่างกันทั้งหมด

ใช่มันเรียกว่า สถาปัตยกรรม. ดูรายละเอียดที่นี่

นี่จะทำให้รายการหนึ่งรายการของเอนทิตีในระดับโลกของคุณ:

List<Entity>

มันเป็นหนึ่งในตัวอย่างขององค์ประกอบมรดก


3

ภายในขอบเขตของคำถามเดิมของคุณมีตัวเลือกหนึ่งที่จะแบ่งรายการออกเป็นการดำเนินการแทนที่จะเป็นประเภทเช่นสิ่งที่คุณมี ตัวอย่างเช่นคุณจะมีList<HasAI>และหนึ่งสำหรับList<Collidable>และเมื่อคุณสร้างวัตถุใหม่มันจะเพิ่มตัวเองลงในรายการการกระทำใด ๆ ที่มันต้องการเมื่อวัตถุถูกทำลายแล้วมันจะลบตัวเองออกจากรายการเหล่านั้น วัตถุสามารถอยู่ในหลายรายการ

ขั้นตอนที่สองของตัวเลือกนั้นคือการ refactor คลาสของคุณจากลำดับชั้นเป็นคลาสที่ใช้อินเตอร์เฟสดังนั้นประเภท HasAI ของคุณเป็นคลาสที่ใช้อินเทอร์เฟซ IBrains เป็นตัวอย่าง การจับคู่ที่List<HasAI>วัตถุเพียงต้องการให้มีส่วนต่อประสาน IBrains

สิ่งนี้จะช่วยล้างความซับซ้อนบางอย่าง


2

ฉันคิดว่าสิ่งที่คุณต้องทำคือนามธรรมการแสดงผลในชั้นเรียนของตัวเองฉันคิดว่าสำหรับผู้เล่นและหนึ่งสำหรับศัตรู (หรืออาจเป็นเพียงหนึ่งสำหรับผู้เล่นแล้วสร้างตัวอย่างของมันสำหรับผู้เล่นและศัตรู - ไม่แน่ใจ 100% การออกแบบเกมของคุณ)

คุณสามารถใช้รูปแบบผู้เยี่ยมชมเพื่อให้ตัวเรนเดอร์วนรอบวัตถุต่าง ๆ และตัดสินใจว่าจะวาดอย่างไรซึ่งอาจซับซ้อนน้อยกว่า


2

การใช้คลาสฐานและการพึ่งพาพหุสัณฐานเป็นความคิดที่ดีมาก แต่มีวิธีการอื่น Noel Llopis มีบทความสองบทความที่ควรค่าแก่การอ่าน ฉันเคยดู Data Oriented Design เมื่อเร็ว ๆ นี้และคิดว่ามันมีข้อดี

บทความที่มีที่นี่และที่นี่ มันอาจทำให้รหัสของคุณซับซ้อนขึ้นเล็กน้อยจากนั้นความแตกต่าง แต่ก็เหมือนกับทุกอย่างของ YMMV ลองดูและดูว่ามันเหมาะกับสิ่งที่คุณพยายามจะทำหรือไม่ ความแตกต่างใช้การสืบทอดและ DOD ใช้การรวมทั้งมีข้อดีข้อเสียดังนั้นเลือกพิษของคุณ


1

คุณสามารถใช้ประโยชน์จาก OOP และความหลากหลายโดยเฉพาะ

โดยพื้นฐานแล้วคุณต้องสร้างคลาสพื้นฐานซึ่งเอนทิตีเกมทั้งหมดสืบทอดมา คลาสพื้นฐานนี้เป็นนามธรรมที่เป็นไปได้มันจะมีสิ่งต่าง ๆ เช่นฟังก์ชั่นการสร้างปรับปรุงและอาจจะทำลาย

จากนั้นคุณจะได้รับออบเจกต์เกมอื่น ๆ ทั้งหมดจากคลาสนี้ คุณอาจจำเป็นต้องเพิ่มการสะท้อนบางอย่างลงในโค้ดของคุณหากภาษาของคุณไม่รองรับการทำสิ่งขั้นสูงเพิ่มเติม แต่ก็สามารถหลีกเลี่ยงได้หากคุณรู้วิธีจัดโครงสร้างการสืบทอดให้ถูกต้อง


1
เขาทำสิ่งนี้ไปแล้ว - ทุกชั้นเรียนเป็นลูกของ GameObject เขาเพียงแค่ต้องการเปลี่ยนชุดรายการของเขาให้เป็นรายการเดียวของ GameObjects
SomeGuy
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.