Pinch to zoom

Hi guys,

I’m having a bit of a problem with my iPhone app. I’m trying to get the Pinch to zoom function working like the normal apps on iPhone which use Pinch to zoom. No i got the zooming part working, only the camera stays at the same position and the FOV changes. Now i want to have the camera zoom in at the point where 2 fingers touch the screen (or the middle), but i can’t seem to get that to work properly.

Here’s my code:

if(Input.touchCount == 2  Input.GetTouch(0).phase == TouchPhase.Moved  Input.GetTouch(1).phase == TouchPhase.Moved)
{
	zooming = true;
	Zoom();
} 

function Zoom()
{ 
	curDist = Input.GetTouch(0).position - Input.GetTouch(1).position;		//Current distance between finger touches
	prevDist = ((Input.GetTouch(0).position - Input.GetTouch(0).deltaPosition) - (Input.GetTouch(1).position - Input.GetTouch(1).deltaPosition));	//Difference in previous locations using delta positions

	touchDelta = curDist.magnitude - prevDist.magnitude;
	speedTouch0 = Input.GetTouch(0).deltaPosition.magnitude / Input.GetTouch(0).deltaTime;
	speedTouch1 = Input.GetTouch(1).deltaPosition.magnitude / Input.GetTouch(1).deltaTime; 
	
	if((touchDelta + varianceInDstances <= 1)  (speedTouch0 > minPinchSpeed)  (speedTouch1 > minPinchSpeed))
	{
		selectedCamera.fieldOfView = Mathf.Clamp(selectedCamera.fieldOfView + (1 * zoomSpeed), 9.5, 60);
	}
	
	if((touchDelta + varianceInDstances > 1)  (speedTouch0 > minPinchSpeed)  (speedTouch1 > minPinchSpeed))
	{
		selectedCamera.fieldOfView = Mathf.Clamp(selectedCamera.fieldOfView - (1 * zoomSpeed), 9.5, 60);
	}
}

Can anyone help me with this?

Just alter your selectedCamera transform.

e.g.

selectedCamera.transform.position += selectedCamera.transform.forward * zoomSpeed;

Doesn’t that just move the camera forward? I’m using the FOV here so the FOV get’s smaller which is zooming in. I want the camera moving to the position where i want to zoom in, or look at that position and zoom in.

Yeah and moving the camera forward or backward is the same as zooming, but without messing up the FOV.
Ok you want to zoom to the point where the finger touches the screen.

Vector2 centerPoint = ( Input.GetTouch(0).position + Input.GetTouch(1).position ) * 0.5f;

you should store this when both fingers touched the screen the first time ( TouchPhase.Began ).

Vector3 worldPoint = selectedCamera.ScreenToWorldPoint( new Vector3( centerPoint.x, centerPoint.y, selectedCamera.farClipPlane ) );
Vector3 direction = worldPoint - selectedCamera.transform.position;
direction.Normalize();

selectedCamera.transform.position += direction * zoomSpeed;

If you want to move the camera to the point and use your FOV zooming.
Just calculate the worldPoint with the nearClipPlane

Vector3 worldPoint = selectedCamera.ScreenToWorldPoint( new Vector3( centerPoint.x, centerPoint.y, selectedCamera.nearClipPlane ) );
selectedCamera.transform.position = worldPoint;

/* Zoom in/out with the FOV method */

Thx for your reply!
I’m still having problems with your code, it’s zooming in and out but only to the right…

Here’s my code:

private var centerPoint : Vector2;

function Update()
{
     if(Input.touchCount == 1  Input.GetTouch(0).phase == TouchPhase.Began  Input.GetTouch(1).phase ==        TouchPhase.Began)
     {
	centerPoint = (Input.GetTouch(0).position + Input.GetTouch(1).position) * 0.5f;
     }
     else if(Input.touchCount == 2  Input.GetTouch(0).phase == TouchPhase.Moved  Input.GetTouch(1).phase == TouchPhase.Moved)
     {
	zooming = true;
	Zoom();
     } 

     function Zoom()
     { 
	curDist = Input.GetTouch(0).position - Input.GetTouch(1).position;		//Current distance between finger touches
	prevDist = ((Input.GetTouch(0).position - Input.GetTouch(0).deltaPosition) - (Input.GetTouch(1).position - Input.GetTouch(1).deltaPosition));	//Difference in previous locations using delta positions
	touchDelta = curDist.magnitude - prevDist.magnitude;
	speedTouch0 = Input.GetTouch(0).deltaPosition.magnitude / Input.GetTouch(0).deltaTime;
	speedTouch1 = Input.GetTouch(1).deltaPosition.magnitude / Input.GetTouch(1).deltaTime; 
	
	var worldPoint : Vector3 = selectedCamera.ScreenToWorldPoint(new Vector3(centerPoint.x, centerPoint.y, selectedCamera.farClipPlane));
	var direction : Vector3 = worldPoint - selectedCamera.transform.position;
	direction.Normalize();
	
	if((touchDelta + varianceInDstances <= 1)  (speedTouch0 > minPinchSpeed)  (speedTouch1 > minPinchSpeed))
	{
		//selectedCamera.fieldOfView = Mathf.Clamp(selectedCamera.fieldOfView + (1 * zoomSpeed), 9.5, 60);
		selectedCamera.transform.position += direction * zoomSpeed;
	}
	
	if((touchDelta + varianceInDstances > 1)  (speedTouch0 > minPinchSpeed)  (speedTouch1 > minPinchSpeed))
	{
		//selectedCamera.fieldOfView = Mathf.Clamp(selectedCamera.fieldOfView - (1 * zoomSpeed), 9.5, 60);
		selectedCamera.transform.position -= direction * zoomSpeed;
	}
     }
}

Ok so i fixed most of the problems, only one persistst. When i’m zooming in with the FOV it works perfectly and zooms in at the position my fingers are pinching. But when i want to zoom out, it keeps zooming in the camera position changes to the left and keeps zooming in.
My code:

private var centerPoint : Vector2;

function Update()
{
  if(Input.touchCount == 2  Input.GetTouch(0).phase == TouchPhase.Began  Input.GetTouch(1).phase ==   TouchPhase.Began)
  {
	centerPoint = (Input.GetTouch(0).position + Input.GetTouch(1).position) * 0.5f;
  }
  else if(Input.touchCount == 2  Input.GetTouch(0).phase == TouchPhase.Moved  Input.GetTouch(1).phase == TouchPhase.Moved)
  {
	zooming = true;
	Zoom();	
  } 
}

function Zoom()
{ 
	curDist = Input.GetTouch(0).position - Input.GetTouch(1).position;		//Current distance between finger touches
	prevDist = ((Input.GetTouch(0).position - Input.GetTouch(0).deltaPosition) - (Input.GetTouch(1).position - Input.GetTouch(1).deltaPosition));	//Difference in previous locations using delta positions
	touchDelta = curDist.magnitude - prevDist.magnitude;
	speedTouch0 = Input.GetTouch(0).deltaPosition.magnitude / Input.GetTouch(0).deltaTime;
	speedTouch1 = Input.GetTouch(1).deltaPosition.magnitude / Input.GetTouch(1).deltaTime; 
	
	var worldPoint : Vector3 = selectedCamera.ScreenToWorldPoint(new Vector3(centerPoint.x, centerPoint.y, selectedCamera.nearClipPlane));
	//var direction : Vector3 = worldPoint - selectedCamera.transform.position;
	//direction.Normalize();
	selectedCamera.transform.position = worldPoint;
	
	if((touchDelta + varianceInDstances <= 1)  (speedTouch0 > minPinchSpeed)  (speedTouch1 > minPinchSpeed))
	{
		selectedCamera.fieldOfView = Mathf.Clamp(selectedCamera.fieldOfView + (1 * zoomSpeed), 9.5, 60);
	}
	
	
	if((touchDelta + varianceInDstances > 1)  (speedTouch0 > minPinchSpeed)  (speedTouch1 > minPinchSpeed))
	{
		selectedCamera.fieldOfView = Mathf.Clamp(selectedCamera.fieldOfView - (1 * zoomSpeed), 9.5, 60);
	}
}

Can someone point out what i’m doing wrong here?

EDIT:
It has something to do with these lines:

var worldPoint : Vector3 = selectedCamera.ScreenToWorldPoint(new Vector3(centerPoint.x, centerPoint.y, selectedCamera.nearClipPlane));

selectedCamera.transform.position = worldPoint;

Because when i comment out selectedCamera.transform.position = worldpoint; i can zoom in properly but then my camera won’t change it’s position.

Guys i’ve been busy for a while now getting the pinch to zoom with vertical panning working. It works ok now but when i zoom in the camera doesn’t change it’s position to the point where i’m touching the screen with 2 fingers. It slides there when zooming in /or out.

my code:

function Update()
{
   if(Input.touchCount == 2  Input.GetTouch(0).phase == TouchPhase.Began  Input.GetTouch(1).phase == TouchPhase.Began)
   {
	centerPoint = (Input.GetTouch(0).position + Input.GetTouch(1).position) * 0.5f;
   }
   else if(Input.touchCount == 2  Input.GetTouch(0).phase == TouchPhase.Moved  Input.GetTouch(1).phase ==   TouchPhase.Moved)
    {
	zooming = true;
	Zoom();
    }

}



function Zoom()
{ 
	curDist = Input.GetTouch(0).position - Input.GetTouch(1).position;		//Current distance between finger touches
	prevDist = ((Input.GetTouch(0).position - Input.GetTouch(0).deltaPosition) - (Input.GetTouch(1).position - Input.GetTouch(1).deltaPosition));	//Difference in previous locations using delta positions
	touchDelta = curDist.magnitude - prevDist.magnitude;
	speedTouch0 = Input.GetTouch(0).deltaPosition.magnitude / Input.GetTouch(0).deltaTime;
	speedTouch1 = Input.GetTouch(1).deltaPosition.magnitude / Input.GetTouch(1).deltaTime; 
	
	var worldPoint : Vector3 = selectedCamera.ScreenToWorldPoint(new Vector3(centerPoint.x, centerPoint.y, selectedCamera.nearClipPlane));
	
	selectedCamera.transform.position = worldPoint;
	
	
	if((touchDelta + varianceInDistances <= 1)  (speedTouch0 > minPinchSpeed)  (speedTouch1 > minPinchSpeed))
	{	
		selectedCamera.fieldOfView = Mathf.Clamp(selectedCamera.fieldOfView + (1 * zoomSpeed), 30, 60);
		if(selectedCamera.fieldOfView >= 60)
			selectedCamera.fieldOfView = 60;
			
	}
	
	
	if((touchDelta + varianceInDistances > 1)  (speedTouch0 > minPinchSpeed)  (speedTouch1 > minPinchSpeed))
	{ 
		selectedCamera.fieldOfView = Mathf.Clamp(selectedCamera.fieldOfView - (1 * zoomSpeed), 30, 60);
		
		if(selectedCamera.fieldOfView <= 30)
			selectedCamera.fieldOfView = 30;

		
	}
}

Can anyone help me with this?