Any examples of an iphone-like scrollview using unity GUI?

#Note - this is now trivial with New Unity UI.

http://docs.unity3d.com/Manual/script-ScrollRect.html

panel the size of the “hole” you want to scroll through, add scrollRect, add mask. make a longer panel with your content. drag the content panel on to “Content” slot on the scrollRect. if the “hole” is the fullscreen, no need for the mask.


Historic question only:

The Unity way of doing scrollviews involves a thumb and a slider on the edges of the screen. Does anybody have a working implementation inside of Unity GUI of something similar to how the iPhone scroll views work?

I.e. I want to be able to drag inside the scroll view itself to drag the contents. Ideally with some kind of vertical/horizontal detection so the movement is constrained to one axis if the user is mostly scrolling along one axis.

Note this also works perfectly for GUILayout.BeginScrollView, if you are using automatic layout.

public class scrollView:MonoBehaviour
{
Vector2 scrollPos;

void OnGUI() // simply an example of a long ScrollView
   { 
    scrollPos = GUI.BeginScrollView(
     new Rect(110,50,130,150),scrollPos,
      new Rect(110,50,130,560),
      GUIStyle.none,GUIStyle.none); 
      // HOORAY THOSE TWO ARGUMENTS ELIMINATE
      // THE STUPID RIDICULOUS UNITY SCROLL BARS
    for(int i = 0;i < 20; i++)
       GUI.Box(new Rect(110,50+i*28,100,25),"xxxx_"+i);
    GUI.EndScrollView ();
   }

void Update()  // so, make it scroll with the user's finger
   {
   if(Input.touchCount == 0) return;
   Touch touch = Input.touches[0];
   if (touch.phase == TouchPhase.Moved)
      {
      // simplistically, scrollPos.y += touch.deltaPosition.y;
      // but that doesn't actually work
      
      // don't forget you need the actual delta "on the glass"
      // fortunately it's easy to do this...
      
      float dt = Time.deltaTime / touch.deltaTime;
      if (dt == 0 || float.IsNaN(dt) || float.IsInfinity(dt))
         dt = 1.0f;
      Vector2 glassDelta = touch.deltaPosition * dt;
      
      scrollPos.y += glassDelta.y;
      }
   }
}

NOTE indeed you almost certainly want to eliminate the ridiculous scroll bars Unity adds to the scroll view. Fortunately that is taken care of by the two “GUIStyle.none” arguments as shown.

ALSO NOTE depending on the “feel” you want on the scroll, for me this is the most ideal approach:

private Vector2 beginFinger;		// finger
private float deltaFingerY; 		// finger
private Vector2 beginPanel; 		// scrollpanel
private Vector2 latestPanel;		// scrollpanel
void Update()
  {
  if ( Input.touchCount != 1 ) return;
  touch = Input.touches[0];
  
  if ( touch.phase == TouchPhase.Began )
    {
    beginFinger = touch.position;
    beginPanel = scrollPos;
    }
  
  if ( touch.phase == TouchPhase.Moved )
    {
    Vector2 newFingerScreenPos = touch.position;
    deltaFingerY = newFingerScreenPos.y - beginFinger.y;
    
    float newY = beginPanel.y + deltaFingerY;
    
    latestPanel = beginPanel;
    latestPanel.y = newY;
    
    scrollPos = latestPanel;
    }
  }

AND FINALLY NOTE you will certainly want to avoid scrolling when the user touches a (eg.) slider. Solution for that issue: How to detect Mouse over gui and guilayout elements? - Questions & Answers - Unity Discussions (selected answer)

For anyone reading this thread and still looking for a pre-made solution, check out EnhancedScroller on the Unity Asset Store: http://u3d.as/fXk