我正在尝试创建一个城市建设者,而我正在编写游戏的一部分,在您实际放置它之前创建一个透明的建筑物渲染。我想做的只是在代码中复制GameObject,修改材质的透明度,删除一些组件,然后实例化它。
存在一个问题:Unity中的所有内容都是通过引用传递的。有没有办法做我想做的事情,或者没有这样的方式吗?
答案 0 :(得分:2)
如果要通过组合在运行时实例化的几个GameObject来创建场景,可以创建一个名为generateEnviroment.cs的脚本(只是一个示例名称),然后您应该将一个或多个GameObjects作为属性从检查器传递给该脚本
下一步是实例化正确的gameObject,然后根据需要修改其属性(位置,大小,材料......)。每个实例都是独立的,具有您可以根据需要修改的属性,并且不会更改同一GameObject的其他实例。
public GameObject customGameObject1;
public GameObject customGameObject2;
void Start()
{
generateEnviroment()
}
void generateEnviroment()
{
//In case you want to add other type of GameObject, like a car or sth you have created:
GameObject myInstantiatedGameObject = GameObject.Instantiate (customGameObject1);
//You change its position
myInstantiatedGameObject.transform.position = new Vector3(0, 0.5F, 0);
// Widen the object by 0.1
myInstantiatedGameObject.transform.localScale += new Vector3(0.1F, 0, 0);
//Change material properties, assuming it has a material component
Renderer rend = myInstantiatedGameObject.GetComponent<Renderer>();
rend.material.shader = Shader.Find("Specular");
rend.material.SetColor("_SpecColor", Color.red);
...
}
你甚至可以在GameObject中添加一个脚本组件,你也可以独立地为每个GameObject实例访问和修改该脚本中的每个属性(变量)(只要你不声明)该属性为静态)
答案 1 :(得分:0)
您无需创建游戏对象的副本。只需实例化它并将值更改为临时放置状态。与设置材料属性一样,在最终放置建筑物时禁用子对象等,只需重置更改。
答案 2 :(得分:0)
实例化是你在Unity中复制对象的方式。
如果实例化对你来说很慢,只需在场景加载时实例化你需要的每个对象,并在需要时禁用/启用它们。
这样您就可以在启用和/或将其移动到最终位置之前更改属性。
以下调用应使其透明。
instantiatedObject.GetComponent<MeshRenderer>().material.color = new Color(0.0f, 0.0f, 0.0f, 0.0f);
请查看以下3个链接:
https://docs.unity3d.com/Manual/InstantiatingPrefabs.html
https://unity3d.com/de/learn/tutorials/topics/scripting/instantiate
答案 3 :(得分:0)
正如大家已经说过的那样,使用GameObject.Instantiate
可以创建预制件或场景对象的副本。您无法延迟对象的 instanitiation (将其置于场景中),但您可以延迟其启动调用(例如Start
和Awake
)。您只需复制一个不活动的对象,修改您想要的任何内容,然后手动激活它。那是你在找什么?
static GameObject InstanitateDelay(GameObject source)
{
bool isActive = source.activeSelf;
source.SetActive(false); // disable it temporarly
var go = Instantiate(source); // create inactive copy
source.SetActive(isActive); // return to previous state
return go; // remeber to activate manually via go.SetActive(true)
}