Làm cách nào để tạo GameObject mới mà không cần thêm nó vào cảnh?


10

Tôi đang tạo ra những gì về cơ bản là hệ thống prefab của riêng tôi. Các đối tượng trò chơi được xác định bởi một tệp dữ liệu có thể đọc được của con người. Tôi muốn tạo một GameObject trống, tải nó với các thành phần được xác định trong tệp dữ liệu và chuẩn bị sẵn sàng và chờ Instantiate()cuộc gọi. Tuy nhiên, bất cứ khi nào tôi sử dụng GameObject go = new GameObject()một đối tượng trò chơi mới sẽ được thêm vào cảnh.

Sử dụng Unity được xây dựng trong prefab, tôi có thể tải prefab dưới dạng GameObject và nó không được thêm vào cảnh. (Xem ví dụ bên dưới)

Lý do đằng sau điều này là tôi muốn có một danh sách chứa GameObjects, một số được tạo bằng cách tải prefab Unity và các danh sách khác được tạo bởi hệ thống prefab tùy chỉnh của tôi. Điều này cần xảy ra trong thời gian chạy và không thể liên quan đến Unity Editor (vì người dùng cuối lý tưởng sẽ có thể xác định tệp dữ liệu của riêng họ).

Làm cách nào tôi có thể tạo GameObject mới mà không có Unity tự động khởi tạo nó cho tôi?


Ví dụ: tôi có thể thực hiện một cuộc gọi như thế này:

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

Và tôi sẽ nhận được một danh sách các GameObject, không ai trong số chúng được thêm vào cảnh khi cuộc gọi được thực hiện. Về cơ bản, tôi đang tạo một LoadAllphương thức cho prefabs của riêng mình và tương tự, tôi không muốn khởi tạo GameObjects khi cuộc gọi được thực hiện.


1
Tôi sợ bạn không thể. Tôi nghĩ bạn sẽ phải trì hoãn việc khởi tạo lớp học của mình.
Roberto

Đã được một thời gian kể từ khi tôi chạm vào Unity, nhưng nếu hóa ra không có cách nào khác, bạn có thể loại bỏ đối tượng khỏi cảnh ngay sau đó và có kết quả mong muốn, chỉ hơi kém hiệu quả?
Kevin Reid

@KevinReid Tôi tin rằng cách duy nhất để làm điều đó là gọi Destroytrên GameObject. Mà loại bỏ nó khỏi hiện trường và phát hành nó, làm cho nó không thể sử dụng.
MichaelHouse

1
@PandaPajama có một ý kiến ​​hay. Gọi go.SetActive(false)là cách tốt nhất để tạo ra một cái gì đó giống như một nhóm đối tượng. Đó không phải là chính xác những gì bạn muốn, nhưng có lẽ bạn có thể có một nhóm nhỏ các đối tượng không hoạt động mà sau đó được nhân bản để khởi tạo tùy chỉnh của bạn.
AndrewEkeren

1
@ Byte56: Tại sao chính xác bạn muốn khởi tạo trước các prefab tùy chỉnh của mình và không chỉ soạn GO với các thành phần bắt buộc khi đang di chuyển trong khi khởi tạo chúng bằng cách sử dụng mô hình giống như nhà máy? Đối với những gì tôi hiểu, bạn muốn cho phép người dùng "tuần tự hóa" prefab bằng cách sử dụng "tệp dữ liệu của riêng họ", vì vậy bạn phải đọc các tệp đó trong thời gian chạy và khởi tạo các thành phần cần thiết .. tôi có thiếu gì không?
Heisenorms

Câu trả lời:


6

Bạn có thể thay đổi HideFlags của GameObject không?

Tôi vừa thử chạy cái này:

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

myGameObject.hideFlags = HideFlags.HideInHierarchy;

... Và nó ở đó, nhưng nó không nằm trong hệ thống phân cấp. Về mặt kỹ thuật, nó ở trong cảnh, nhưng bạn không nhìn thấy nó cho đến khi bạn thay đổi cờ trở lại thành HideFlags. Đó không phải là câu trả lời mà bạn đang tìm kiếm, nhưng ít nhất là khi phát hành điều này cho các nhà phát triển, nó sẽ tốt hơn là nhóm các đối tượng của bạn.


1
Điều này, kết hợp với việc vô hiệu hóa nó (vì vậy không có đoạn script nào thực thi), có thể hoạt động. Tôi sẽ thử và cho bạn biết. Đây vẫn là một công việc xung quanh, nhưng tôi nghĩ đó là những gì tôi còn lại ở thời điểm này. Và, đối với tất cả những gì chúng ta biết, đây có thể là những gì được thực hiện trong nội bộ, mặc dù tôi nghi ngờ nó.
MichaelHouse

1
@ Byte56: Tôi cũng nghĩ đó là một cách giải quyết, nhưng thực sự tôi đã phát hiện ra rằng Unity thực hiện chính xác điều tương tự khi xem trước hoạt hình: nó khởi tạo trò chơi ẩn trong cảnh và đưa chúng vào khung xem trước bằng máy ảnh chuyên dụng. Vì vậy, có thể nó không nghe có vẻ sạch sẽ, nhưng thực sự giải pháp này dường như cũng được sử dụng trong nội bộ.
Heisenorms

1
Xin lỗi vì đã chấp nhận muộn. Tôi chỉ có xung quanh để thực hiện điều này và nó hoạt động rất tốt. Cảm ơn.
MichaelHouse

0

Thật không may, bạn không thể làm điều đó chính xác. Tuy nhiên, bạn có thể thực hiện cùng một mẫu thiết kế (nghĩa là trừu tượng hóa việc xây dựng các đối tượng của bạn và sau đó chỉ cần gọi chúng bằng một lệnh duy nhất sau đó) thông qua một mẫu Factory .

Khi bạn muốn một đối tượng, hãy gọi một cái gì đó như thế Factory.CreateGameEntity(), và phương thức đó sẽ xử lý mọi thứ phía sau hậu trường.


Nó phức tạp hơn bạn nghĩ, làm cho nó không sạch sẽ. Tôi sẽ đăng một câu trả lời sẽ có đầy đủ chi tiết, nhưng về cơ bản trình phân tích cú pháp phải khá phức tạp. Ví dụ: nếu tôi muốn kiểm tra xem prefab có thành phần nào không, trước khi khởi tạo, nó đơn giản như GetComponent<>() != null. Với các tệp dữ liệu của tôi, trình phân tích cú pháp phải tìm kiếm thành phần chính xác trong dữ liệu. Tương tự để có được một giá trị từ bên trong một thành phần, v.v. Các GameObjectlớp học cung cấp rất nhiều chức năng mà cần phải được nhân đôi bởi các phân tích cú pháp.
MichaelHouse

Nếu bạn có thể cung cấp bằng chứng hoặc thậm chí một số lý do cho lý do tại sao điều này không thể được thực hiện, nó sẽ làm cho câu trả lời này hoàn thành.
MichaelHouse

Tôi sẽ thấy sau này nếu tôi có thể tìm thấy bất kỳ tài liệu hướng dẫn dứt khoát về vấn đề này, vì bây giờ tất cả tôi có thể tìm được những chủ đề diễn đàn forum.unity3d.com/threads/... - answers.unity3d.com/questions/366273/... - answers.unity3d .com / câu hỏi / 19736 /
Hoài

0

Không có cách nào để làm go = new GameObject();mà không thêm nó vào cảnh.

Tôi đang làm việc trên một RTS nơi cơ sở người chơi cần phải kiên trì và về cơ bản, chúng tôi tuần tự hóa mọi thứ họ đã thực hiện và tải lại trong thời gian chạy bằng cách sử dụng các tài sản được sửa đổi từ cửa hàng.

Hầu hết đầu ra thành XML hoặc JSON, do đó, thật dễ dàng để tải tệp và thao tác nó theo ý muốn.


Cảm ơn Marc. Bạn có thể cung cấp bằng chứng hoặc lý do cho việc không thể tạo GameObject mới mà không thêm nó vào cảnh không? Tôi có mã tuần tự của riêng mình, vì vậy đó không phải là vấn đề, cảm ơn vì lời đề nghị.
MichaelHouse

-1

Cách đúng đắn là tạo một prefab, bạn phân bổ prefab đó làm Object, sau đó bất cứ khi nào bạn muốn khởi tạo chỉ cần sử dụng tham chiếu của Object này và sử dụng nó làm GameObject.

Ví dụ :

private Object prefab;


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

1
Đó là sử dụng hệ thống prefab hiện có. Như câu hỏi của tôi, về cơ bản, tôi đang tạo ra hệ thống prefab của riêng mình. Một phần của các yêu cầu là "không thể liên quan đến Trình chỉnh sửa Unity". Tạo một prefab sử dụng Unity Editor.
MichaelHouse

Điều đó bạn không thể làm, bạn sẽ cần giấy phép cho nhà phát triển sử dụng SDK của họ để có thể tạo dữ liệu của riêng bạn. Trừ khi tôi sai, họ sẽ không chia sẻ mã của họ mà không có bling bling. Nhưng tôi biết một số người đã có thể xuất cảnh từ Unity sang công cụ trò chơi của riêng họ
Ericool 30/03/2015

Chà, rõ ràng là có thể vì tôi đã tạo ra hệ thống prefab của riêng mình bằng cách sử dụng câu trả lời đã chọn. Bạn có thể tìm hiểu làm thế nào để làm điều đó trong khóa học tôi đã tạo, được tìm thấy trong hồ sơ của tôi.
MichaelHouse

không nhờ Tôi là một người tốt nghiệp trò chơi lập trình :) Vâng, nếu bạn thành công vĩ đại đó cho bạn, không cần nó để làm cho trò chơi
Ericool

Đây là một hệ thống về cơ bản cho phép người dùng cuối thực hiện prefabs. Điều này khá hữu ích trong các trò chơi dành cho mod và nội dung do người dùng cuối tạo ra. (Vì vậy, tôi nghĩ rằng nó khá hữu ích trong việc tạo ra các trò chơi).
MichaelHouse

-1

Để tải prefab vào một biến để bạn có thể khởi tạo nó sau, bạn sẽ sử dụng mã sau:

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

Tôi đã thực hiện điều này trong một dự án với Unity 5.5. Nó sẽ có sẵn để khởi tạo nhưng không có trong cảnh hoặc một phần của hệ thống phân cấp cho đến khi được khởi tạo như bình thường.


Tôi cảm thấy bạn đã đọc sai câu hỏi. Câu trả lời này liên quan đến việc sử dụng hệ thống prefab mặc định . Câu hỏi này hỏi trong bối cảnh tạo ra một hệ thống prefab tùy chỉnh , nơi mà điều này không thể truy cập được. Ví dụ ở phía dưới phục vụ để làm nổi bật hơn nữa điều này.
Gnemlock

"Làm cách nào tôi có thể tạo GameObject mới mà không có Unity tự động khởi tạo nó cho tôi?" Là câu hỏi đã được hỏi và mã này đã trả lời nó. Mã có thể được thay đổi để có được kết quả mong muốn với các hệ thống tải tùy chỉnh.
darthhawk

Đây thực chất là những gì tôi mô tả trong ví dụ có trong câu hỏi. Và nó hoạt động tốt cho prefabs, nhưng không phải để tạo các đối tượng trò chơi mới từ các tệp dữ liệu.
MichaelHouse
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.