I'm trying to make a script to set an object when is being instantiated. The problem is, I don't clearly know how to do it. I have this function..
function spawnPlayer()
{
var CameraScript = GameObject.Find(PlayerPrefab.name).GetComponent("Camera Control");
Network.Instantiate(PlayerPrefab, spawnObject.position, Quaternion.identity, 0);
}
Where PlayerPrefab is going to be the Prefab that's going to be instantiated. When this happens, I need to set the instantiated gameObject on another GameObject which is camera and has a script called "Camera Control" and inside there's a transform Target which I'm trying to set. How to do this?
The code you posted can't be right. You are using the PlayerPrefab's name to to find the Camera Control script attached to the camera? By that logic then the moment you instantiate PlayerPrefab, on the second line, you will have a second camera.
I think what you want to do is this: Instantiate the player prefab and make the camera point to the player.
So I am assuming the CameraControl script is created. You need the following before we start to code.
Attach CameraControl script to the camera in the scene.
Make sure the Player script is attached to the Player Prefab.
Have a third script that will instantiate the PlayerPrefab. I will call it Instantiator. Attach it to an empty GameObject in the scene, think of it as the world GameObject. We will call it World.
Make sure the Instantiator script is attached to the World GameObject and that it is pointing to the PlayerPrefab.
Code: Instantiator
The Instantiator script will spawn and create things we will use in the scene.
#pragma strict
var PlayerPrefab : GameObject;
function Start ()
{
// You can add position and rotation to the function call if you like.
var p = Instantiate(PlayerPrefab) as GameObject;
// Find the camera script and point to Player's transform.
Camera.main.GetComponent("CameraControl").SendMessage("setTarget", p.transform);
}
Notice I used the fact that the MainCamera in the scene is marked by Unity for you so it is easy to find.
Code: CameraControl
The CameraControl will have the logic to follow the Player as you see fit. Notice that target will point to what the camera will focus on. Of course following the Player around you will have to write.
var target : Transform;
function setTarget(t : Transform)
{
target = t;
}
I just taught myself a bit of JavaScript. I had never used it before.
I found my solution.
What I was meaning on my question was to set my camera's script the transform of the instantiated object.
I did not have to make many empty objects with scripts value of each object; it took me hours to find it because I did not know how unity handles the scripts objects calls.
This is how I made it:
var PlayerPrefab : GameObject;
var spawnObject : Transform;
private var MainCamera : GameObject;
function spawnPlayer()
{
var player = Instantiate(PlayerPrefab, spawnObject.position, Quaternion.identity);
MainCamera = GameObject.Find("MainCamera");
player.name = "Ball";
if(MainCamera)
{
MainCamera.GetComponent.<CameraControl>().target = player.transform;
Debug.Log("Succeed.");
}
}
Like this, my camera will have the transform properties of the new instantiated object automatically.
Related
enter image description here I am instantiating prefabs and listing them on a scroll list. I am trying to teleport the player to instantiated prefab position when I click its reference on scroll list listing?
All suggestions are welcome.
From what I understand about your problem (explained in the comments rather than the question), you should be able to do this:
You can instantaneously move an object camera by setting its transform's position to the instantiated prefab's position when the click has occurred. For a camera, you probably have the camera view in X and Y dimension, so you want to move it to the new X and Y position but leave the Z-position as it is.
One potential solution: Add the following script to the GameObject with your Button component. Then add an event-listener on the Button component that points to the newly added script component and choose the MyTeleportingButton.OnClick as the target method. You also need to drag in the camera as a reference in the new script component.
public class MyTeleportingButton : MonoBehaviour
{
public GameObject camera;
public void OnClick()
{
// casting to Vector2 in order to move in 2D only
var currentPosition = camera.transform.position;
var newPosition = transform.position;
// set same depth as camera
newPosition.z = currentPosition.z;
camera.transform.position = newPosition;
}
}
I want to destroy the instantiated bullet holes and bullet sparks prefabs at the point of raycast hit after few seconds , here's the code i'm using to instantiate them
if(Physics.Raycast(transform.position,transform.TransformDirection(Vector3.forward)*100,hitShot)) {
var rotation = Quaternion.FromToRotation( Vector3.up, hitShot.normal );
var instantiatedExplosion : GameObject = Instantiate(
hitParticles, hitShot.point, rotation );
var rotation1 = Quaternion.FromToRotation(Vector3.forward,hitShot.normal);
var instantiatedHole: GameObject =Instantiate (bulletHoles,hitShot.point,rotation1);
}
Never used Unity with JavaScript. However, I think the APIs give you the same method for destruction as for C#, so try this:
Destroy(bulletHole, time);//public static void Destroy(Object obj, float t = 0.0F);
https://docs.unity3d.com/ScriptReference/Object.Destroy.html
I suppose you are new in Unity, normally you try to not destroy GameObjects like bullets, bullet holes, bullet sparkles etc. (or any gameObject you can reuse) because you can reuse them saving a lot of performance. See Object Pooling
I have the following simple prefab:
When I add this to my scene, it looks like this:
Very neat!
Then I have the following script on my Character:
public class MageController : MonoBehaviour {
public GameObject Spell;
public float SpellSpeed;
// Use this for initialization
void Start () {
}
// Update is called once per frame
void Update () {
if (Input.GetKeyDown(KeyCode.H)) {
GameObject newSpell = Instantiate(Spell);
newSpell.transform.position = transform.position;
newSpell.transform.rotation = Quaternion.LookRotation(transform.forward, transform.up);
Rigidbody rb = newSpell.GetComponent<Rigidbody>();
rb.AddForce(newSpell.transform.forward * SpellSpeed);
}
}
}
The goal is of course to make sure that the fireball is spawned correctly (with the tail behind it)
This works when I stand at 0.0.0; it looks like this:
However, if I turn around it looks like this:
As you can see, the rotation of the fireball is not correct (in the above incorrect image it is flying away from me, however, the tail is in front).
What am I doing wrong? How can I make sure that the tail is always correctly placed?
Update after following the guidance of PlantProgrammer
it still turns incorrectly :(
Look at the image below!
You want to use the forward direction of the player and not it's rotation, when instantiating the fireball. (Remember: transform in your script is the player transform not the fireball transform.) Check https://docs.unity3d.com/ScriptReference/Quaternion.LookRotation.html. LookRotation will return the rotation based on player's forward and up vectors.
GameObject newSpell = Instantiate(Spell);
newSpell.transform.position = transform.position;
newSpell.transform.rotation = Quaternion.LookRotation(transform.forward, transform.up);
Not part of your question, but I would also suggest letting the fireball fly in the forward direction of itself not the player (as this leaves more room for later modifications)
rb.AddForce(newSpell.transform.forward * SpellSpeed);
I am working on a 2D game and have created a game object using C# script as below. I also set my camera to orthogonal and have adjusted my sprite based on the width of the screen. Regardless of the position I set, the object is always at the center of the screen. How can I solve this?
using UnityEngine;
using System.Collections;
public class TestingPositions : MonoBehaviour {
GameObject hero;
Sprite heroSprite;
Vector3 heroPosition;
// Use this for initialization
void Start () {
hero = new GameObject ();
Instantiate (hero, heroPosition, Quaternion.identity);
Camera camera = GameObject.FindGameObjectWithTag ("MainCamera").GetComponent<Camera> ();
heroPosition = camera.ScreenToWorldPoint(new Vector3(Screen.width/4, Screen.height/4, camera.nearClipPlane));
heroSprite = Resources.Load <Sprite> ("Sprites/heroImage");
SpriteRenderer renderer = hero.AddComponent<SpriteRenderer>(); renderer.sprite = heroSprite;
}
}
when you use Instantiate you have to use it on
an existing model.
Instantiate means "duplicate this model" or "copy this model", or "make a new one, using this model as an example".
What you are doing, is creating a brand new empty "hero" game object - and then "instantiating" it. That is meaningless and does nothing.
What you must do whenever you want to use "Instantiate" is this:
public GameObject modelPerson;
Note that the name must be "modelSomething".
first put that in your code. LOOK at the Inspector. MAKE your actual model hero (or whatever it is)
Sit it somewhere off camera where it is not seen.
Now, drag that thing to the "modelPerson" slot in the Inspector.
If you are not familiar with the basics of using Inspector-dragging in Unity, review basic Unity tutorials https://unity3d.com/learn/tutorials/topics/scripting
Next in your code, perhaps in Start, try this
GameObject newHero = Instantiate( modelPerson );
newHero.transform.position = .. whatever you want
newHero.transform.rotation = .. whatever you want
newHero.name = "Dynamically created";
newHero.transform.parent = .. whatever you want
once you understand these basics, there is very much more to learn about Instantiate. You can ask that in separate questions. Good luck.
Your need to save the reference to your gameObject that is created with Instantiate, because Instantiate makes a copy not modifies the original.
To modify a gameobjects position after instantiation, you need to use gameobject.transform.position = newPosition; To modify it before instantiation, you would need to do the "heroPosition" line before using heroPosition in Instantiate.
So like this:
using UnityEngine;
using System.Collections;
public class TestingPositions : MonoBehaviour
{
GameObject hero;
SpriteRenderer heroSprite;
// Use this for initialization
void Start()
{
Camera camera = GameObject.FindGameObjectWithTag("MainCamera").GetComponent<Camera>();
//Save the reference to the instantiated object into a variable
//Since you are creating an object from scratch, you don't even need Instantiate, which means copy - not create.
hero = new GameObject();
//Set its position
hero.transform.position = camera.ScreenToWorldPoint(new Vector3(Screen.width / 4, Screen.height / 4, camera.nearClipPlane));
//Set its rotation
hero.transform.rotation = Quaternion.identity;
//Add sprite renderer, save the reference
heroSprite = hero.AddComponent<SpriteRenderer>();
//Assign the sprite
heroSprite.sprite = Resources.Load<Sprite>("Sprites/heroImage");
}
}
I'm trying to implement a tower defense game in Unity, and I can't figure out how can I assign a velocity or a force to a new instantiated object (in the creator object's script)
I have a tower which is supposed to shoot a bullet towards the enemy which triggered its collider. This is the script of the towers:
function OnTriggerEnter(other:Collider){
if(other.name=="Enemy")
{
ShootBulletTo(other.transform);
}
}
function ShootBulletTo(target:Transform)
{//public var Bullet:Transform
var BulletClone = Instantiate(Bullet,transform.position, Quaternion.identity); // ok
BulletClone.AddForce(target.position); //does not compile since Transform.AddForce() does not exist.
}
I guess the problem is I have to use a Transform variable for instantiate but I need a GameObject variable for velocity, force etc. So how can I instantiate the bullet with initial velocity?
Thanks for help.
You have to acces the rigidbody component of your bullet clone to change the force, not the transform.
Here's how your code should look:
function OnTriggerEnter(other:Collider)
{
if(other.name=="Enemy")
{
ShootBulletTo(other.transform);
}
}
function ShootBulletTo(target:Transform)
{
var Bullet : Rigidbody;
BulletClone = Instantiate(Bullet, transform.position, Quaternion.identity);
BulletClone.AddForce(target.position);
}
There's also a good example in the unity script reference
http://docs.unity3d.com/Documentation/ScriptReference/Object.Instantiate.html
[EDIT] I'm pretty sure, that you don't want to add the enemies position as a force, instead you should add a direction that goes towards the enemies position.
You subtract two positions to gain a direction vector between them, so the ShootBulletTo function should look like this:
function ShootBulletTo(target:Transform)
{
// Calculate shoot direction
var direction : Vector3;
direction = (target.position - transform.position).normalized;
// Instantiate the bullet
var Bullet : Rigidbody;
BulletClone = Instantiate(Bullet, transform.position, Quaternion.identity);
// Add force to our bullet
BulletClone.AddForce(direction);
}