วิธีสร้าง GameObject ใหม่โดยไม่เพิ่มเข้าไปในที่เกิดเหตุ?


10

ฉันกำลังสร้างสิ่งที่เป็นพื้นฐานของระบบ prefab ของฉันเอง วัตถุของเกมถูกกำหนดโดยไฟล์ข้อมูลที่มนุษย์สามารถอ่านได้ ฉันต้องการสร้าง GameObject ที่ว่างเปล่าโหลดด้วยส่วนประกอบที่กำหนดในไฟล์ข้อมูลและเตรียมให้พร้อมและรอการInstantiate()โทร อย่างไรก็ตามเมื่อใดก็ตามที่ฉันใช้GameObject go = new GameObject()วัตถุเกมใหม่จะถูกเพิ่มเข้าไปในที่เกิดเหตุ

การใช้ Unity ที่สร้างในรูปแบบสำเร็จรูปฉันสามารถโหลดรูปแบบสำเร็จรูปเป็น GameObject และมันไม่ได้เพิ่มเข้าไปในฉาก (ดูตัวอย่างด้านล่าง)

เหตุผลที่อยู่เบื้องหลังนี้คือฉันต้องการมีหนึ่งรายการที่มี GameObjects บางรายการสร้างขึ้นโดยการโหลด Unity prefab และอื่น ๆ ที่สร้างขึ้นโดยระบบ prefab ที่กำหนดเองของฉัน สิ่งนี้ต้องเกิดขึ้นในเวลาทำงานและไม่สามารถมีส่วนร่วมกับ Unity Editor (เนื่องจากผู้ใช้ปลายทางจะสามารถกำหนดไฟล์ข้อมูลของตัวเองได้)

ฉันจะสร้าง GameObject ใหม่โดยไม่มีความเป็นเอกภาพในการสร้างอินสแตนซ์ให้ฉันอัตโนมัติได้อย่างไร


ตัวอย่างเช่นฉันสามารถโทรออกเช่นนี้

Resources.LoadAll("PrefabsDirectory", typeof(GameObject))

และฉันจะได้รับรายชื่อ GameObjects ซึ่งจะไม่มีการเพิ่มเข้าไปในที่เกิดเหตุเมื่อมีการโทรออก โดยพื้นฐานแล้วฉันกำลังสร้างLoadAllวิธีการสำหรับ prefab ของตัวเองและในทำนองเดียวกันฉันไม่ต้องการยกตัวอย่าง GameObjects เมื่อมีการโทร


1
ฉันเกรงว่าคุณทำไม่ได้ ฉันคิดว่าคุณจะต้องชะลอการเริ่มเรียนของคุณ
Roberto

เป็นเวลานานแล้วที่ข้าได้สัมผัส Unity แต่ถ้าปรากฎว่ามันไม่มีทางรอบ ๆ นี้เจ้าช่วยนำวัตถุออกจากฉากทันทีหลังจากนั้นและได้ผลตามที่ต้องการเพียงเล็กน้อยอย่างไม่มีประสิทธิภาพหรือไม่?
Kevin Reid

@ KevininReid ฉันเชื่อว่าวิธีเดียวที่จะทำเช่นนั้นคือการเรียกDestroyGameObject ซึ่งจะลบมันออกจากฉากและปล่อยออกมาทำให้มันใช้ไม่ได้
MichaelHouse

1
@PandaPajama มีความคิดที่ดี การเรียกgo.SetActive(false)เป็นวิธีที่ดีที่สุดในการสร้างบางสิ่งบางอย่างเช่นกลุ่มวัตถุ มันไม่ใช่สิ่งที่คุณต้องการอย่างแน่นอน แต่บางทีคุณอาจมีกลุ่มวัตถุที่ไม่ใช้งานกลุ่มเล็ก ๆ ที่ถูกโคลนหลังจากการสร้างอินสแตนซ์ของคุณเอง
AndrewEkeren

1
@ Byte56: ทำไมคุณต้องการที่จะสร้างอินสแตนซ์ prefab ที่กำหนดเองไว้ล่วงหน้าและไม่เพียง แต่เขียน GO ด้วยองค์ประกอบที่จำเป็นในขณะที่สร้างอินสแตนซ์โดยใช้โรงงานเช่นรูปแบบ? สำหรับสิ่งที่ฉันเข้าใจว่าคุณต้องการอนุญาตให้ผู้ใช้ "prefab" prefab ใช้ "ไฟล์ข้อมูลของตัวเอง" ดังนั้นคุณต้องอ่านไฟล์เหล่านั้นในเวลาทำงานต่อไปและยกตัวอย่างส่วนประกอบที่จำเป็น ..
Heisenbug

คำตอบ:


6

คุณสามารถเปลี่ยนธงแบนเนอร์ของ GameObject ได้หรือไม่

ฉันแค่ลองใช้สิ่งนี้:

GameObject myGameObject = new GameObject ();
myGameObject.name = "Obvious Name";

myGameObject.hideFlags = HideFlags.HideInHierarchy;

... และมันอยู่ที่นั่น แต่มันไม่ได้อยู่ในลำดับชั้น ในทางเทคนิคมันอยู่ในฉาก แต่คุณไม่เห็นมันจนกว่าคุณจะเปลี่ยนมันธงกลับไปเป็น HideFlags ไม่มี มันไม่ใช่คำตอบที่คุณกำลังมองหา แต่อย่างน้อยที่สุดเท่าที่การปล่อยสิ่งนี้ให้กับนักพัฒนามันจะสะอาดกว่าการจัดกลุ่มวัตถุของคุณ


1
สิ่งนี้จับคู่กับการปิดการใช้งาน (ดังนั้นจึงไม่มีสคริปต์ทำงาน) สามารถใช้งานได้ ฉันจะลองและแจ้งให้คุณทราบ มันยังคงเป็นงานอยู่ แต่ฉันคิดว่านั่นคือสิ่งที่ฉันทิ้งไว้ตอนนี้ และสำหรับทุกสิ่งที่เรารู้นี่อาจเป็นสิ่งที่ทำขึ้นภายในแม้ว่าฉันจะสงสัย
MichaelHouse

1
@ Byte56: ฉันคิดว่ามันเป็นวิธีแก้ปัญหาด้วยเหมือนกัน แต่จริง ๆ แล้วฉันค้นพบว่าวันนี้ Unity ทำสิ่งเดียวกันเมื่อดูตัวอย่างภาพเคลื่อนไหว: มันทำให้เกมที่ซ่อนอยู่ในฉากแสดงตัวอย่างและแสดงในกรอบตัวอย่างด้วยกล้อง ดังนั้นบางทีมันอาจจะไม่ได้เสียงที่ดีนัก แต่ที่จริงแล้วโซลูชันนี้ดูเหมือนว่าจะใช้ภายในเช่นกัน
Heisenbug

1
ขออภัยที่รับสาย ฉันเพิ่งจะนำมันไปใช้และมันก็ใช้งานได้ดีมาก ขอบคุณ
MichaelHouse

0

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

เมื่อคุณต้องการวัตถุให้เรียกสิ่งที่ชอบFactory.CreateGameEntity()และวิธีการนั้นจะจัดการทุกอย่างที่อยู่เบื้องหลัง


มันซับซ้อนกว่าที่คุณคิด แต่ทำให้มันไม่สะอาด ฉันจะโพสต์คำตอบจะเต็มรายละเอียด แต่เป็นหลัก parser จะต้องมีความซับซ้อนสวย ตัวอย่างเช่นถ้าผมต้องการที่จะทดสอบถ้าสำเร็จรูปมีส่วนประกอบก่อน instantiating GetComponent<>() != nullมันเป็นง่ายๆเป็น ด้วยไฟล์ข้อมูลของฉัน parser จะต้องค้นหาส่วนประกอบที่ถูกต้องในข้อมูล เช่นเดียวกับการรับค่าจากภายในองค์ประกอบและอื่น ๆ GameObjectระดับให้มากของการทำงานที่จะต้องทำซ้ำโดยแยกวิเคราะห์เป็น
MichaelHouse

หากคุณสามารถให้หลักฐานหรือแม้กระทั่งเหตุผลบางประการว่าทำไมไม่สามารถทำมันได้ก็จะทำให้คำตอบนี้เสร็จสมบูรณ์
MichaelHouse

ฉันจะได้เห็นต่อไปว่าฉันสามารถหาเอกสารที่ชัดเจนใด ๆ เกี่ยวกับเรื่องนี้สำหรับตอนนี้ทั้งหมดที่ฉันสามารถหาเหล่านี้ฟอรั่มหัวข้อforum.unity3d.com/threads/... - answers.unity3d.com/questions/366273/... - answers.unity3d .com / คำถาม / 19736 / …
jhocking

0

ไม่มีวิธีทำgo = new GameObject();โดยไม่เพิ่มเข้าไปในฉาก

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

เอาต์พุตส่วนใหญ่ไปยัง XML หรือ JSON ดังนั้นมันจึงค่อนข้างตรงไปตรงมาที่จะโหลดไฟล์และจัดการตามที่คุณต้องการ


ขอบคุณมาร์ค คุณสามารถให้หลักฐานหรือเหตุผลที่ไม่สามารถสร้าง GameObject ใหม่โดยไม่เพิ่มลงในฉากได้หรือไม่? ฉันมีรหัสซีเรียลไลซ์เซชั่นของตัวเองดังนั้นจึงไม่ใช่ปัญหาขอบคุณสำหรับคำแนะนำ
MichaelHouse

-1

วิธีที่ถูกต้องคือการสร้าง prefab คุณจะจัดสรร prefab นั้นเป็นวัตถุจากนั้นเมื่อใดก็ตามที่คุณต้องการสร้างอินสแตนซ์ให้ใช้การอ้างอิงของออบเจ็กต์นี้และใช้เป็น GameObject

เช่น

private Object prefab;


public static GameObject Create(void)
{
   return (Instantiate(prefab , position , rotation) as GameObject);
}

1
นั่นคือการใช้ระบบสำเร็จรูปที่มีอยู่ ตามคำถามของฉันฉันจะสร้างระบบรูปแบบสำเร็จรูปของตัวเองเป็นหลัก ส่วนหนึ่งของข้อกำหนดคือ "ไม่สามารถเกี่ยวข้องกับ Unity Editor" การสร้าง prefab ใช้ Unity Editor
MichaelHouse

อย่างที่คุณทำคุณจะต้องมีใบอนุญาตสำหรับผู้พัฒนาซอฟต์แวร์โดยใช้ SDK ของพวกเขาเพื่อให้สามารถสร้างข้อมูลของคุณเองได้ นอกจากว่าฉันผิดพวกเขาจะไม่แบ่งปันรหัสของพวกเขาโดยไม่มีการกะพริบใด ๆ แต่ฉันรู้ว่าบางคนสามารถส่งออกฉากจาก Unity ไปยังโปรแกรมเกมของตัวเองได้
Ericool

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

ไม่เป็นไรฉันเป็นโปรแกรมเมอร์เกมที่จบแล้ว :) ถ้าคุณประสบความสำเร็จอย่างยอดเยี่ยมสำหรับคุณไม่จำเป็นต้องใช้มันในการทำเกม
Ericool

เป็นระบบที่ช่วยให้ผู้ใช้งานสร้าง prefab ได้ สิ่งนี้มีประโยชน์ในเกมสำหรับ mod และเนื้อหาที่ผู้ใช้สร้างขึ้น (ใช่แล้วฉันคิดว่ามันค่อนข้างมีประโยชน์ในการทำเกม)
MichaelHouse

-1

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

 GameObject ball = (GameObject)(Resources.Load ("myPrefab"));

ฉันทำสิ่งนี้ในโครงการที่มี Unity 5.5 จะสามารถใช้อินสแตนซ์ได้ แต่จะไม่อยู่ในฉากหรือบางส่วนของลำดับชั้นจนกระทั่งอินสแตนซ์เป็นปกติ


ฉันรู้สึกว่าคุณอ่านคำถามผิด คำตอบนี้เกี่ยวข้องกับการใช้ระบบ prefab เริ่มต้น คำถามนี้ถามในบริบทของการสร้างระบบสำเร็จรูปที่กำหนดเองซึ่งไม่สามารถเข้าถึงได้ ตัวอย่างที่ด้านล่างทำหน้าที่เพื่อเน้นเพิ่มเติมนี้
Gnemlock

"ฉันจะสร้าง GameObject ใหม่โดยไม่มีความเป็นเอกภาพโดยอัตโนมัติสำหรับฉันได้อย่างไร" เป็นคำถามที่ถามและรหัสนี้ตอบมัน รหัสสามารถเปลี่ยนแปลงได้เพื่อให้ได้ผลลัพธ์ที่ต้องการด้วยระบบการโหลดที่กำหนดเอง
darthhawk

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