2010-07-16 19 views
38

Ok .. Debo estar pasando por alto algo muy simple aquí, pero creo que estoy tratando de hacer algo bastante básico .. Simplemente mantener la posición de la barra de desplazamiento de un cambio de orientación en ScrollView ...ScrollView .scrollTo not working? Ahorro de la posición en la rotación ScrollView

Aquí está el código para mi onSaveInstanceState y onRestoreInstanceState. sView es el contenedor para el diseño de ScrollView. Dentro de mi scrollview hay una distribución lineal con muchas textviews.

@Override 
public void onSaveInstanceState(Bundle outState) 
{ 
    //---save whatever you need to persist— 

    outState.putInt("sViewX",sView.getScrollX()); 
    outState.putInt("sViewY",sView.getScrollY()); 

super.onSaveInstanceState(outState); 

} 

@Override 
public void onRestoreInstanceState(Bundle savedInstanceState) 
{ 
    super.onRestoreInstanceState(savedInstanceState); 

    sViewX = savedInstanceState.getInt("sViewX"); 
    sViewY = savedInstanceState.getInt("sViewY"); 

    sView.scrollTo(sViewX, sViewY); 

} 

Si fijo una tostada con los valores de sViewX y sViewY en la restauración, los valores se mantienen y correcta.

Editar: Traté de hacer un sView.scrollTo (0,150); en mi onCreate ... solo para ver si eso abriría la actividad a 150px hacia abajo, y no fue así. Creo que mi problema tiene que ver con el método .scrollTo.

+1

Como referencia, si usa fragmentos, onRestoreInstanceState tiene que ir en el método de activación de actividad(). Además, recuerde verificar: if (savedInstanceState! = Null) –

Respuesta

111

Lo descubrí.

Desde que estoy usando setText a TextViews en mi onCreate, llamando .scrollTo no va a funcionar.

Así que ahora estoy usando lo siguiente:

sView.post(new Runnable() { 
    @Override 
    public void run() { 
     sView.scrollTo(sViewX, sViewY); 
    } 
}); 
+0

Cuando lo he probado sin hilo, ¿no tendrá ningún efecto y así? –

+7

¡No lo entiendo, pero parece funcionar! Gracias. –

+0

Esto realmente tiene sentido, pero cuando intento aplicar esto a una vista web, no funciona. – TacB0sS

0

Para MVVMCross:

protected override void OnSaveInstanceState(Bundle outState) 
{ 
    base.OnSaveInstanceState(outState); 

    ScrollView sv = FindViewById<ScrollView>(Resource.Id.dispatchScrollView); 
    int posY = sv.ScrollY; 

    outState.PutInt("scrollY", posY); 
} 

protected override void OnRestoreInstanceState(Bundle savedInstanceState) 
{ 
    base.OnRestoreInstanceState(savedInstanceState); 

    ScrollView sv = FindViewById<ScrollView>(Resource.Id.dispatchScrollView); 
    int posY = savedInstanceState.GetInt("scrollY"); 

    sv.Post(new Runnable(new Action(() => sv.ScrollTo(0, posY)))); 
} 
1

onRestoreInstanceState() es simplemente demasiado pronto para desplazar la vista. Es por eso que publicar nuevos Runnable ayuda, pero no siempre. A veces incluso hay que usar postDelayed() para que funcione. para el fragmento se puede utilizar onViewCreated() en su lugar:

@Override 
public void onViewCreated(View view, Bundle savedInstanceState) { 
    super.onViewCreated(view, savedInstanceState); 
    sViewX = savedInstanceState.getInt("sViewX"); 
    sViewY = savedInstanceState.getInt("sViewY"); 
    sView.scrollTo(sViewX, sViewY); 
} 
1

Esto es trabajo para mí

@Override 
protected void onSaveInstanceState(Bundle outState) { 
    outState.putInt(SystemGlobal.SCROLL_Y, mRelativeLayoutMain.getTop()); 
} 

@Override 
protected void onRestoreInstanceState(Bundle savedInstanceState) { 
    // TODO Auto-generated method stub 
    super.onRestoreInstanceState(savedInstanceState); 
    mRelativeLayoutMain.scrollTo(0, savedInstanceState.getInt(SystemGlobal.SCROLL_Y)); 
} 
0

Usted debe comenzar de desplazamiento antes de sacar los componentes, ya que de desplazamiento no funciona componentes untill no se crean:

@Override 
public void onWindowFocusChanged(boolean hasFocus) { 
    scrollView.scrollTo(.... 
0

en lugar de enviar la acción de desplazamiento para la próxima carrera de circuito, puede desplazarse a la vista de devolución de llamada layout global:

@Override 
public void onRestoreInstanceState(Bundle savedInstanceState) { 
    super.onRestoreInstanceState(savedInstanceState); 
    sView.getViewTreeObserver().addOnGlobalLayoutListener(
     new ViewTreeObserver.OnGlobalLayoutListener() { 
      @Override 
      public void onGlobalLayout() { 
       sView.scrollTo(sViewX, sViewY); 
      } 
     } 
    ); 
}