Spawning in Unity: Spheres flying out of range - c#

I am programming a game in Unity. I am trying to spawn a sphere in space everytime the user clicks the interface. I can spawn the spheres, but the spheres are always at coordinates of around (200,200, 0) and (400,400,0), but the spheres should be spawned at where the pointer is on the screen. It's my code below, can someone help? I am writing in C#:
using UnityEngine;
using System.Collections;
public class myscript : MonoBehaviour {
//initialize a circle
public GameObject Node;
public float cooldown = 1;
bool clicker;
float clicktime = 0;
GameObject node; //reference to the prefab
// Use this for initialization
void Start () {
}
//In everyframe you can
void Update () {
clicker = Input.GetMouseButtonDown(0); //obtaining the input
clicktime += Time.deltaTime;
}
//Check whether you can shoot
void FixedUpdate(){
if (clicker == true && clicktime >= cooldown) { //if the clicker is clicked and the previos clicking is done
SpawnCircle(); //spawn a circle
clicktime = 0; //reset timer
}
}
void SpawnCircle(){
//this creates a new game object
x = Input.mousePosition.x
y = Input.mousePosition.
node = GameObject.Instantiate (Node,Input.mousePosition,Quaternion.identity) as GameObject;
//settings that we initalize our object with
//node.transform.position = new Vector3(Input.mousePosition.x, Input.mousePosition.y,0);
}
}

You need to calculate ScreenToWorld Coordinates. With Unity it's easy actually.
https://unity3d.com/learn/tutorials/modules/beginner/physics/raycasting

Related

(Unity C#) NPC not moving on Grass and other terrain

I have created a NPC that follows the main player. When the player is in a certain range of the NPC, the NPC is supposed to walk, run, and attack based on the distance between the player and the NPC. The NPC has an Animator, box collider, Nav Mesh Agent, Enemy Animator And Enemy Controller Script attached. The settings are as follows,
My problem is that the NPC does not chase the player if there's some sort of grass or ferns on the terrain.
The NPC is set to run all types of terrain using Nav Mesh Agent, moreover the bake settings are like in the image. A video of the issue can be seen here.
The code of the enemy controller (although I doubt that is the issue) is as follows:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.AI;
public enum EnemyState
{
PATROL,
CHASE,
ATTACK
}
public class EnemyController : MonoBehaviour
{
private EnemyAnimator enemy_Anim;
private NavMeshAgent navAgent;
private EnemyState enemy_State;
public float walk_Speed = 0.5f;
public float run_Speed = 4f;
public float chase_Distance = 7f;
private float current_Chase_Distance;
public float attack_Distance = 1.8f;
public float chase_After_Attack_Distance = 2f;
public float patrol_Radius_Min = 20f, patrol_Radius_Max = 60f;
public float patrol_For_This_Time = 15f;
private float patrol_Timer;
public float wait_Before_Attack = 2f;
private float attack_Timer;
private Transform target;
public GameObject attack_Point;
//private EnemyAudio enemy_Audio;
void Awake()
{
enemy_Anim = GetComponent<EnemyAnimator>();
navAgent = GetComponent<NavMeshAgent>();
target = GameObject.FindWithTag(Tags.PLAYER_TAG).transform;
// enemy_Audio = GetComponentInChildren<EnemyAudio>();
}
// Use this for initialization
void Start()
{
enemy_State = EnemyState.PATROL;
patrol_Timer = patrol_For_This_Time;
// when the enemy first gets to the player
// attack right away
attack_Timer = wait_Before_Attack;
// memorize the value of chase distance
// so that we can put it back
current_Chase_Distance = chase_Distance;
}
// Update is called once per frame
void Update()
{
if (enemy_State == EnemyState.PATROL)
{
Patrol();
}
if (enemy_State == EnemyState.CHASE)
{
Chase();
}
if (enemy_State == EnemyState.ATTACK)
{
Attack();
}
}
void Patrol()
{
// tell nav agent that he can move
navAgent.isStopped = false;
navAgent.speed = walk_Speed;
// add to the patrol timer
patrol_Timer += Time.deltaTime;
if (patrol_Timer > patrol_For_This_Time)
{
SetNewRandomDestination();
patrol_Timer = 0f;
}
if (navAgent.velocity.sqrMagnitude > 0)
{
enemy_Anim.Walk(true);
}
else
{
enemy_Anim.Walk(false);
}
// test the distance between the player and the enemy
if (Vector3.Distance(transform.position, target.position) <= chase_Distance)
{
enemy_Anim.Walk(false);
enemy_State = EnemyState.CHASE;
// play spotted audio
// enemy_Audio.Play_ScreamSound();
}
} // patrol
void Chase()
{
// enable the agent to move again
navAgent.isStopped = false;
navAgent.speed = run_Speed;
// set the player's position as the destination
// because we are chasing(running towards) the player
navAgent.SetDestination(target.position);
if (navAgent.velocity.sqrMagnitude > 0)
{
enemy_Anim.Run(true);
}
else
{
enemy_Anim.Run(false);
}
// if the distance between enemy and player is less than attack distance
if (Vector3.Distance(transform.position, target.position) <= attack_Distance)
{
// stop the animations
enemy_Anim.Run(false);
enemy_Anim.Walk(false);
enemy_State = EnemyState.ATTACK;
// reset the chase distance to previous
if (chase_Distance != current_Chase_Distance)
{
chase_Distance = current_Chase_Distance;
}
}
else if (Vector3.Distance(transform.position, target.position) > chase_Distance)
{
// player run away from enemy
// stop running
enemy_Anim.Run(false);
enemy_State = EnemyState.PATROL;
// reset the patrol timer so that the function
// can calculate the new patrol destination right away
patrol_Timer = patrol_For_This_Time;
// reset the chase distance to previous
if (chase_Distance != current_Chase_Distance)
{
chase_Distance = current_Chase_Distance;
}
} // else
} // chase
void Attack()
{
navAgent.velocity = Vector3.zero;
navAgent.isStopped = true;
attack_Timer += Time.deltaTime;
if (attack_Timer > wait_Before_Attack)
{
enemy_Anim.Attack();
attack_Timer = 0f;
// play attack sound
// enemy_Audio.Play_AttackSound();
}
if (Vector3.Distance(transform.position, target.position) > attack_Distance + chase_After_Attack_Distance)
{
enemy_State = EnemyState.CHASE;
}
} // attack
void SetNewRandomDestination()
{
float rand_Radius = Random.Range(patrol_Radius_Min, patrol_Radius_Max);
Vector3 randDir = Random.insideUnitSphere * rand_Radius;
randDir += transform.position;
NavMeshHit navHit;
NavMesh.SamplePosition(randDir, out navHit, rand_Radius, -1);
navAgent.SetDestination(navHit.position);
}
void Turn_On_AttackPoint()
{
attack_Point.SetActive(true);
}
void Turn_Off_AttackPoint()
{
if (attack_Point.activeInHierarchy)
{
attack_Point.SetActive(false);
}
}
public EnemyState Enemy_State
{
get; set;
}
} // class
I would appreciate very it if someone could help with such an issue!
EDIT: I forgot to add the grass settings, these are as follows. As you can see there are no colliders.
I am digging some more and apparently the only walkable area is as follows (not entire map), how can I adjust this?
Below is how I did:
Painted the terrain with all kinds of grasses I needed and trees.
Undone all the painted grasses and trees.
Baked the navigation mesh(Navmesh) onto the terrain.
Redone all the painted grasses and trees.
Boom! Work done. :)
Why Do grasses not walkable?
Grasses have been painted like trees hence they are carved during baking process as trees.
Trick:
You have to paint the grasses and all the trees needed, then you have to unpaint all the grasses exceptional for the trees. After that bake the terrain, and undone the process(pressing CTRL + Z several times) until you see the grasses repainted.

How to shoot ball to Touch X position Unity 3D?

I have a ball on a ground, and when touching the screen I want to shoot it to the X position of the Touch. Do you have any suggestions?
This is the code I have so far:
public Rigidbody Ball;
public float Speed = 50f;
void FixedUpdate () {
if(ClickDone == false){
if (Input.GetMouseButton(0)){
ClickDone = true;
Ball.velocity = transform.forward * Speed;
}
}
}
here is your new code :
using UnityEngine;
public class GoToTouch : MonoBehaviour
{
public Camera cam;//put your main camera here
public float speed;//Speed of movement
Vector3 LastTouch;
void Start()
{
LastTouch = Vector3.zero;
}
void Update()
{
//We check for new touches etch frame
if (Input.touchCount> 0)
LastTouch = Input.touches[0].rawPosition;
//We move towards the last touch
if(LastTouch != Vector3.zero)transform.position=
Vector3.Lerp(transform.position,cam.ScreenToWorldPoint(LastTouch),speed*Time.DeltaTime);
}
}
what is important for you to look at is the
ScreenToWorldPoint function LastTouch holds the actual pixel the user touched
after ScreenToWorldPoint you get the position that the pixel he touched represent in the
world. Good luck learning !

Unity 2D C# gameObject does not activate other gameObjects if statements when colliding with each other. Why?

The way this game works is that the game starts off with a Largest Ball. When the rocket hits the large ball it splits into two medium balls and then into two small balls. When the rocket hits the smallest ball it gets destroyed.
The problem I'm having is that when the rocket collides with the ball. The rocket gets destroyed, but the ball does "not" divide into two Large balls and so forth.
I just noticed this and I'm wondering if my problem will be fixed if I turn this code statement to == "smallest ball" instead of !=.
if (target.tag == "Rocket")
{
if (gameObject.tag != "Smallest Ball")
{
InstantializeBallsonoff();
}
else {
AudioSource.PlayClipAtPoint(popsounds[Random.Range(0, popsounds.Length)], transform.position);
//play random audio in the popsounds array at current position of ball
gameObject.SetActive(false); //deactivate the gameobject
}
}
}//ontriggerenter
This is the full code for my ball Script
using UnityEngine;
using System.Collections;
public class Ball : MonoBehaviour {
private float forceX, forceY;
private Rigidbody2D ball;
[SerializeField]
private bool moveLeft, moveRight;
[SerializeField]
private GameObject originalBall;
private GameObject ball1, ball2;
private Ball ball1script, ball2script;
[SerializeField]
private AudioClip[] popsounds; //array
// Use this for initialization
void Awake () {
ball = GetComponent<Rigidbody2D>();
ballspeed();
}
// Update is called once per frame
void Update () {
ballmovement();
}
void InstantiatingBalls()
{
if (this.gameObject.tag != "Smallest Ball")
{
ball1 = Instantiate(originalBall); //create copy of originalball into ball1
ball2 = Instantiate(originalBall);
ball1.name = originalBall.name;
ball2.name = originalBall.name;
ball1script = ball1.GetComponent<Ball>(); //get the ball script
ball2script = ball2.GetComponent<Ball>();
}
}//InstantiatingBalls
void InstantializeBallsonoff() {
InstantiatingBalls();
Vector3 temp = transform.position; //start from current ball location
ball1.transform.position = temp;
ball1script.setmoveLeft(true);
ball2.transform.position = temp;
ball2script.setmoveRight(true);
ball1.GetComponent<Rigidbody2D>().velocity = new Vector2(0, 2.5f); //x,y
ball2.GetComponent<Rigidbody2D>().velocity = new Vector2(0, 2.5f); //x,y
AudioSource.PlayClipAtPoint(popsounds[Random.Range(0, popsounds.Length)], transform.position);
//play random audio in the popsounds array at current position of ball
gameObject.SetActive(false); //deactivate the gameobject
}//InstantializeBallsonoff
public void setmoveLeft(bool moveLeft) { //canMoveLeft
this.moveLeft = moveLeft;
this.moveRight = !moveLeft; //moveRight is now false b/c we set moveLeft to true
}
public void setmoveRight(bool moveRight) {//canMoveRight
this.moveRight = moveRight;
this.moveLeft = !moveRight;
}
void ballmovement() {
if (moveLeft) {
Vector3 temp = transform.position; //current position of ball
temp.x -= Time.deltaTime; // represent time per frame
transform.position = temp;
}
if (moveRight) {
Vector3 temp = transform.position; //current position of ball
temp.x += Time.deltaTime; // represent time per frame
transform.position = temp;
}
}
void ballspeed() {
forceX = 2.5f;
switch (this.gameObject.tag) {
//this refers to gameobject that holds this script
case "Largest Ball":
forceY = 11.5f;
break;
case "Large Ball":
forceY = 10.5f;
break;
case "Medium Ball":
forceY = 9f;
break;
case "Small Ball":
forceY = 8f;
break;
case "Smallest Ball":
forceY = 7f;
break;
}//switch
}//ballspeed
void OnTriggerEnter2D (Collider2D target) {
if (target.tag == "Ground") {
ball.velocity = new Vector2(0, forceY);
}
if (target.tag == "Right Wall") {
setmoveLeft(true);
/*moveRight = false;
moveLeft = true;*/
}
if (target.tag == "Left Wall")
{
setmoveRight(true);
/*moveRight = true;
moveLeft = false;*/
}
if (target.tag == "Rocket")
{
if (gameObject.tag != "Smallest Ball")
{
InstantializeBallsonoff();
}
else {
AudioSource.PlayClipAtPoint(popsounds[Random.Range(0, popsounds.Length)], transform.position);
//play random audio in the popsounds array at current position of ball
gameObject.SetActive(false); //deactivate the gameobject
}
}
}//ontriggerenter
}//ball
This is partial of my code where the rocket gets destroyed when it collides with the large ball & the top. This is the other part that I am having trouble with.
void OnTriggerEnter2D(Collider2D target) {
if (target.tag == "Top") {
Destroy(gameObject);
}
string[] ballhit = target.name.Split();
/*array ballhit
split = deletes the space between two words and make it so it takes 2 spaces in the array*/
for (int s = 0; s < ballhit.Length; s++) {
Debug.Log("The array contains: " +ballhit [s]);
if (ballhit.Length > 1)
{ //ball names will always be more than 1 length "Largest Ball"
if (ballhit[1] == "Ball")
{
Destroy(gameObject);
}//destroy object
}//ballhit name length
}// name increments
}//triggerCollider
This is my full Rocket Script
using UnityEngine;
using System.Collections;
public class Rocket : MonoBehaviour {
private Rigidbody2D rocket;
private float speed = 5f;
// Use this for initialization
void Awake () {
rocket = GetComponent<Rigidbody2D>();
}
// Update is called once per frame
void Update () {
rocket.velocity = new Vector2(0, speed); //x, y rocket movement
}
void OnTriggerEnter2D(Collider2D target) {
if (target.tag == "Top") {
Destroy(gameObject);
}
string[] ballhit = target.name.Split();
/*array ballhit
split = deletes the space between two words and make it so it takes 2 spaces in the array*/
for (int s = 0; s < ballhit.Length; s++) {
Debug.Log("The array contains: " +ballhit [s]);
if (ballhit.Length > 1)
{ //ball names will always be more than 1 length "Largest Ball"
if (ballhit[1] == "Ball")
{
Destroy(gameObject);
}//destroy object
}//ballhit name length
}// name increments
}//triggerCollider
}//rocket
Your code is much more complicated than it needs to be an therefore the actual error is difficult to find.
First off, your moveLeft and moveRight bools are mutually exclusive. You need only one of them. I would event prefer to replace both with a public int currentDirection which you set to 1 for right and -1 for left.
Your new ballMovement method could then simply be:
void MoveBall() // C# methods are upper-case by convention
{
transform.position += Vector3.right * currentDirection * Time.deltaTime;
}
The way you check with which type of ball you are colliding is not very safe. I would suggest you use an enum to differentiate the ball sizes.
public enum BallSizes { Largest, Large, Medium, Small, Smallest }; // The different possible values
public BallSize size = BallSizes.Largest; // The balls current size, the biggest size by default
This also allows you to store your y-axis force values in a matching array and access them easily without the use of a switch or else-if:
private float[] forcesY = new float[]{ 11.5f, 10.5f, 9f, 8f, 7f };
void SetBallSpeed()
{
forceX = 2.5f;
forceY = forcesY[(int)size];
}
I think the problem you had with the ball not splitting is is connected to this.
Upon collision, you detected the type of ball you collided with, by examining its tag. But you always Instantiate the new balls using the same prefab, and I never saw you change the tag. So what type of ball are you creating?
If you use the method I described above, you can simply assign a general tag "Ball" and handle the rest with the BallSizes-enum. When creating the new balls you can do the following:
[SerializedField] // The SerializedField property makes it show up in the inspector, even though it is private
private Ball ballPrefab; // Attention: Type "Ball"
public void IsHit() // Method to execute upon rocket collision
{
if(ball.size != BallSizes.Smallest)
{
Ball leftBall = Instantiate(ballPrefab). // Notice that, when you assign you prefab as Type "Ball", you directly get the Ball-Component as the return value.
leftball.direction = -1;
leftball.size = (BallSizes)(size + 1); // Add one to size, to get get the next enum value, which is the next smaller size.
Ball rightBall = .... // Do same stuff for the right ball
}
Destroy(this.gameObject);
}
I don't know how you plan to visualise the type of ball, but you might want to add a float[] ballScales, which you use to shrink the ball's actual size, something like: leftBall.transform.localScale = Vector3.one * ballScales[(int)size].
Finally, another reason your collision does not work might well be, that you handle it in two different places. If you destroy the rocket after it detects collision with the ball, nothing has happend to the ball yet. If the ball is checking for collision afterward it will most likely not find the rocket, because you already destroyed it. A clean way to solve this, would be to let the rocket notify the ball of the collision:
void OnTriggerEnter2D(Collider2D target)
{
if(target.tag == "Top")
Destroy(gameObject);
else if(target.tag == "Ball")
{
target.GetComponent<Ball>().IsHit(); // We know this component should exist when the object is tagged "Ball"
Destroy(gameobject);
}
}
You can then remove that from you ball collision and shorten it to this:
void OnTriggerEnter2D (Collider2D target)
{
if(target.tag == "Ground")
ball.velocity = new Vector2(0, forceY);
if(target.tag == "Right Wall" || target.tag == "Left Wall")
direction *= -1; // Inverts the direction, + <-> -
}
Phew, that was a lot.
I hope this is still relevant and answers more questions than it raises.
Happy coding!

Disable rigidbody on a specific gameobject using C# and Unity

I'm having trouble in my pinch code because it also grabs my player. Here is my code:
using UnityEngine;
using System.Collections;
using Leap;
using Leap.Unity;
/**
* Detects pinches and grabs the closest rigidbody if it's within a given range.
*
* Attach this script to the physics hand object assinged to the HandController in a scene.
*/
public class MagneticPinch : MonoBehaviour {
public const float TRIGGER_DISTANCE_RATIO = 0.7f;
/** The stiffness of the spring force used to move the object toward the hand. */
public float forceSpringConstant = 100.0f;
/** The maximum range at which an object can be picked up.*/
public float magnetDistance = 0.5f;
protected bool pinching_;
protected Collider grabbed_;
public GameObject TrashAudio;
public GameObject myPlayer;
void Start() {
pinching_ = false;
grabbed_ = null;
}
/** Finds an object to grab and grabs it. */
void OnPinch(Vector3 pinch_position) {
pinching_ = true;
// Check if we pinched a movable object and grab the closest one that's not part of the hand.
Collider[] close_things = Physics.OverlapSphere(pinch_position, magnetDistance);
Vector3 distance = new Vector3(magnetDistance, 0.0f, 0.0f);
for (int j = 0; j < close_things.Length; ++j) {
Vector3 new_distance = pinch_position - close_things[j].transform.position;
if (close_things[j].GetComponent<Rigidbody>() != null && new_distance.magnitude < distance.magnitude &&
!close_things[j].transform.IsChildOf(transform)) {
grabbed_ = close_things[j];
distance = new_distance;
}
}
}
/** Clears the pinch state. */
void OnRelease() {
grabbed_ = null;
pinching_ = false;
TrashAudio.gameObject.SetActive (false);
//ActivateRigidbody ();
}
/**
* Checks whether the hand is pinching and updates the position of the pinched object.
*/
void Update() {
bool trigger_pinch = false;
HandModel hand_model = GetComponent<HandModel>();
Hand leap_hand = hand_model.GetLeapHand();
if (leap_hand == null)
return;
// Scale trigger distance by thumb proximal bone length.
Vector leap_thumb_tip = leap_hand.Fingers[0].TipPosition;
float proximal_length = leap_hand.Fingers[0].Bone(Bone.BoneType.TYPE_PROXIMAL).Length;
float trigger_distance = proximal_length * TRIGGER_DISTANCE_RATIO;
// Check thumb tip distance to joints on all other fingers.
// If it's close enough, start pinching.
for (int i = 1; i < HandModel.NUM_FINGERS && !trigger_pinch; ++i) {
Finger finger = leap_hand.Fingers[i];
for (int j = 0; j < FingerModel.NUM_BONES && !trigger_pinch; ++j) {
Vector leap_joint_position = finger.Bone((Bone.BoneType)j).NextJoint;
if (leap_joint_position.DistanceTo(leap_thumb_tip) < trigger_distance)
trigger_pinch = true;
}
}
Vector3 pinch_position = hand_model.fingers[0].GetTipPosition();
// Only change state if it's different.
if (trigger_pinch && !pinching_)
OnPinch(pinch_position);
else if (!trigger_pinch && pinching_)
OnRelease();
//this line of code is a self scripting for disabling the rigidbody from the player component
// Accelerate what we are grabbing toward the pinch.
if (grabbed_ != null) {
Vector3 distance = pinch_position - grabbed_.transform.position;
//DeactivateRigidbody (); //this is not to grab the rigidbody of the player
grabbed_.GetComponent<Rigidbody> ().AddForce (forceSpringConstant * distance);
TrashAudio.gameObject.SetActive (true);
//DeactivateRigidbody ();
}
}
}
Every object must have a rigidbody that is set to USE GRAVITY so my player as well so that it will not go through my terrain . My script is grabs the nearest object that has a rigidbody. The problem is when I grab some object its always grab itself I mean my player. I'm using a leap motion to grab.
So how can I obtain that if my script detects that it is grabbing my player it will stop grabbing but instead grab the object?
Really easy.
You can tag your player like player like in image:
then add to your code something like this into the method OnPinch
// Check if we pinched a movable object and grab the closest one that's not part of the hand.
Collider[] close_things = Physics.OverlapSphere(pinch_position, magnetDistance);
Vector3 distance = new Vector3(magnetDistance, 0.0f, 0.0f);
for (int j = 0; j < close_things.Length; ++j) {
if(close_things[j].gameobject.Tag.ToUppercase() == "PLAYER")
continue; //here you jump to a the next object
PS: Or you can simply use a different layer that ignore the player
By using
//attach this script to pinching
void DeactivateRigid(){
myPlayer.Getcomponent<Rigidbody>().isKenimatic == false;
myPlayer.Getcomponent<Rigidbody().detectCollision = true;
}
//attach this script to release
void ActivateRigid(){
...
}
My Unity is a bit rusted but you can attach a tag to GameObject, https://docs.unity3d.com/ScriptReference/GameObject-tag.html
Be sure to tag the player as a player, afterwards you could use a check whether the nearest gameobjects tag isn't "player".

Unity C# Make two Sprites move to each other

So I'm new to Unity, but creating a simple 2D game. I need to make two sprites move to each other when clicking on them. I want to use a script attached to the Main Camera but open for other suggestions. Thanks friends!
Here is my script:
public class MoveTo : MonoBehaviour {
GameObject objectA = null;
GameObject objectB = null;
// Use this for initialization
void Start () {
}
// Update is called once per frame
void Update () {
if(Input.GetMouseButtonDown(0))
{
Ray rayOrigin = Camera.main.ScreenPointToRay(Input.mousePosition);
RaycastHit hitInfo;
if(Physics.Raycast(rayOrigin, out hitInfo))
{
//Destroy (hitInfo.collider.gameObject);
if(objectA == null)
{
objectA = hitInfo.collider.gameObject;
}
else{
objectB = hitInfo.collider.gameObject;
}
if(objectA != null && objectB != null)
{
//Need something to make them move towards each other here???
objectA = null;
objectB = null;
}
}
}
}
}
In my opinion moving other gameObjects with a script attached to the camera is breaking the basic idea of components in Unity. It would also be very hard to do if you want the objects to move smoothly and also be able to have multiple pairs of objects moving at same time. You would need some kind of list of moving objects and their destinations. Then you would need to go through the list in the update function of the camera script and update all positions of sprite gameObjects.
I think it is better to attach simple inbetweening script like below to the gameObjects of the sprites.
using UnityEngine;
using System.Collections;
public class Tweener : MonoBehaviour {
public float tweenStopDistance = 0.2f;
public float tweenSpeed = 2.0f;
public Vector3 targetPosition = new Vector3();
void Start () {
targetPosition = transform.position;
}
void Update () {
if((transform.position - targetPosition).magnitude > tweenStopDistance){
transform.position += tweenSpeed * (targetPosition - transform.position).normalized * Time.deltaTime;
}
}
}
In this case you just need to calculate the target position in your camera script.
if(objectA != null && objectB != null)
{
// Calculate position in the middle
Vector3 target = 0.5f * (objectA.transform.position + objectB.transform.position);
// Set middle position as tween target
objectA.GetComponent<Tweener>().targetPosition = target;
objectB.GetComponent<Tweener>().targetPosition = target;
objectA = null;
objectB = null;
}
If you have lot of those sprites and not much computation power on your target machine. You could also attach that script component at run time with gameObject.AddComponent for those sprites that need it. Attaching is probably quite heavy but you wouldn't need to test for already being in the target for sprites that are not moving.

Categories