pas de gravité pour scrollview. comment créer du contenu dans scrollview comme centre

105

Je veux que le contenu à l'intérieur du scrollView soit au centre.

<ScrollView
    android:id="@+id/scroller"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:paddingTop="12dp"
    android:paddingBottom="20dp"
    android:scrollbarStyle="outsideOverlay"
    android:layout_gravity="center" >

    <Button 
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content" 
        android:text="check" 
        android:gravity="center_vertical|center_horizontal"/>

</ScrollView>

Remarque: il n'y a pas d' android:gravityattribut pour scrollvew.

tout sol: -

Padma Kumar
la source

Réponses:

176

J'ai eu le même problème et je l'ai finalement compris. C'est pour une verticale ScrollView.

Placez votre ScrollViewintérieur RelativeLayoutet centrez-le dans le RelativeLayout. Pour que cela fonctionne, vous ScrollViewdevez avoir

android:layout_height="wrap_content"

Voici à quoi devrait ressembler le code final:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent">

    <ScrollView
        android:id="@+id/scrollView1"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content" 
        android:layout_centerVertical="true" >

        <LinearLayout
            android:id="@+id/linearLayout1"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="vertical">

            <Button
                android:id="@+id/button1"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="b1"/>
            <Button
                android:id="@+id/button2"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="b2"/>
            <Button
                android:id="@+id/button3"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="b3"/>
        </LinearLayout>

    </ScrollView>

</RelativeLayout>
hadi
la source
29
Celui-ci semble mieux fonctionner pour moi que la réponse acceptée. Je vous remercie!
Patrick Boos
Idéalement, Android devrait examiner ces problèmes lorsqu'il existe une hiérarchie de mise en page. Devrait également fournir les deux options de défilement (horizontal / vertical) dans un scrollview.BTW merci @hadi
mayank_droid
2
C'est un peu un hack, donc même si cela fonctionne bien, cela ne va pas.
DariusL
3
Hé ça marche, mais ne défile pas quand le clavier est visible, j'ai essayé d'ajouter un manifeste android:windowSoftInputMode="stateHidden|adjustResize"mais, ne faites pas défiler, aidez-moi s'il vous plaît
Helio Soares Junior
3
Pas besoin d'utiliser lourd RelativeLayoutcomme vue racine. Il peut être FrameLayoutet android:layout_gravity="center_vertical"pourScrollView
GrafOrlov
148

Que dis-tu de ça?

<?xml version="1.0" encoding="utf-8"?>
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/scrollView1"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:paddingTop="12dp"
    android:paddingBottom="20dp"
    android:scrollbarStyle="outsideOverlay" >


    <LinearLayout
        android:id="@+id/linearLayout1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="vertical" 
        android:layout_gravity="center"
        android:gravity="center">

        <Button
            android:id="@+id/button1"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="check" 
            android:gravity="center_vertical|center_horizontal"/>
    </LinearLayout>

</ScrollView>
Fantôme
la source
2
Ouais! Que diriez-vous de ça! Cela a fonctionné à merveille pour moi, alors merci beaucoup, gentil monsieur.
RileyE
Impressionnant! Cela m'a sauvé aussi! Thanks :)
marienke
101
Il y a un problème avec cela. Si votre contenu dans ScrollView est plus grand que le scrollview, il le centrera toujours et coupera le contenu en haut (je ne sais pas encore pourquoi). Cela signifie que vous ne pouvez pas y faire défiler.
Patrick Boos
7
PatrickBoos a raison; cela ne semble pas fonctionner. Utilisez la réponse de hadi ci-dessous, en centrant verticalement la vue de défilement dans un RelativeLayout.
Mason Lee
Oui, de cette façon, un bug, un contenu plus grand que scrollView, le contenu ne défilera pas vers le haut, son top est un nombre négatif, étrange :(
Kross
98

Je pense qu'une solution plus élégante serait d'utiliser la ScrollViewde » android:fillViewportla propriété. A ScrollViewest un peu différent dans la façon dont il traite sa vue de contenu (ne peut en avoir qu'une), même si vous définissez match_parent( fill_parent) sur la, ScrollViewcela ne donnera pas autant d'espacement à sa vue de contenu, au lieu de cela, le comportement par défaut est pour ScrollViewle contenu indépendamment de ce que vous spécifiez pour cette vue. Ce que android:fillViewportfait, c'est dire au ScrollViewpour étirer son contenu pour remplir la fenêtre ( http://developer.android.com/reference/android/widget/ScrollView.html#attr_android:fillViewport ). Donc, dans ce cas, votre LinearLayoutserait étiré pour correspondre à la fenêtre et si la hauteur va derrière la fenêtre, elle pourra faire défiler ce qui est exactement ce que vous voulez!

La réponse acceptée ne fonctionnera pas correctement lorsque le contenu s'étend au-delà de, ScrollViewcar elle centrera toujours la vue du contenu en le coupant d'abord une partie de la vue, et le ScrollViewcentré dans une autre mise en page fonctionne mais ne semble tout simplement pas correct, en plus Je pense que cela entraînera également une erreur de peluches (parent inutile ou quelque chose du genre).

Essayez quelque chose comme ceci:

<ScrollView
    android:id="@+id/scroller"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:paddingTop="12dp"
    android:paddingBottom="20dp"
    android:scrollbarStyle="outsideOverlay"
    android:fillViewport="true">

    <LinearLayout
        android:id="@+id/content"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="vertical"
        android:gravity="center">

        <Button
            android:id="@+id/button"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="check" />

    </LinearLayout>

</ScrollView>

Rappelez-vous simplement que la raison pour laquelle il est centré ici maintenant est à cause du android:gravitysur le LinearLayoutcar le ScrollViewva s'étirer LinearLayoutalors gardez cela à l'esprit en fonction de ce que vous ajoutez à la mise en page.

Une autre bonne lecture sur ScrollViewmais pas au sujet de centrage mais environ fillViewportest http://www.curious-creature.org/2010/08/15/scrollviews-handy-trick/

Brian Ethier
la source
11
Cela ressemble à l'implémentation la plus correcte, aucune vue supplémentaire n'est requise.
DariusL
1
Belle solution, semble être la plus propre pour moi. Merci pour elle
Benjamin Scharbau
2
Fonctionne mieux que la réponse acceptée, vous m'avez fait gagner beaucoup de temps! Vraiment bravo Brian Ethier!
Mattia Ruggiero
C'est la bonne solution, pour toutes les raisons qui y sont décrites. Si vous essayez la solution ci-dessus, et que votre vue de défilement est plus large que votre écran, vous aurez en effet une partie de votre vue de défilement inaccessible et ne pourrez pas y faire défiler. . Cela devrait être accepté comme la solution appropriée
Speckpgh
1
Stackoverflow typique .. la bonne solution est souvent quelque part au milieu.
Teovald du
14

Utilisez cet attribut dans ScrollView

android:fillViewport="true"

Exemple

 <?xml version="1.0" encoding="utf-8"?>
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:scrollbarStyle="outsideOverlay"
android:fillViewport="true"
>
   <RelativeLayout
              android:layout_width="match_parent"
              android:layout_height="wrap_content">

         <!--Your Code goes here-->

   </RelativeLayout>

</ScrollView>

Assurez-vous d'utiliser Single Child dans ScrollView, comme dans l'exemple ci-dessus, Relativelayout.

Abhishek Garg
la source
@JoshuaKing peut parce que c'est une question de 7 ans et j'ai posté cette réponse récemment il y a 9 mois.
Abhishek Garg
Ha! oh .. vérité. 😆Eh bien, cela a parfaitement fonctionné! Donc merci!
Joshua King
1
Cela devrait certainement être la réponse acceptée! Il fonctionne parfaitement et centre un ScrollView si le contenu est inférieur à la taille du conteneur. Fonctionne à la fois pour ScrollView et HorizontalScrollView. Merci beaucoup! 💝💖
Ray Li
cela peut avoir l'effet involontaire d'étirer votre contenu dans la vue de défilement
martinseal1987
@ martinseal1987 Je pense que l'effet dépendra de votre composant enfant, que de la manière dont vous créez votre mise en page, bien que si cela ne fonctionne pas pour vous, vous pouvez créer votre propre composant de vue de défilement personnalisé selon vos besoins de conception et de travail. et veuillez également partager la capture d'écran du résultat souhaité avec moi, afin que je puisse examiner et vous fournir une solution plus efficace et plus fonctionnelle. prêt à aider. à votre santé.
Abhishek Garg
9

Pour @Patrick_Boss - ce qui a empêché le contenu de couper dans mon application était de changer la gravité et layout_gravity en center_horizontal pour le LinearLayout.

Cela a fonctionné pour moi ... mais je ne sais pas si cela fonctionnera pour vous.

Modification de la réponse de @ Ghost -

<?xml version="1.0" encoding="utf-8"?>
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/scrollView1"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:paddingTop="12dp"
    android:paddingBottom="20dp"
    android:scrollbarStyle="outsideOverlay" >


    <LinearLayout
        android:id="@+id/linearLayout1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="vertical" 
        android:layout_gravity="center_horizontal"
        android:gravity="center_horizontal">

        <Button
            android:id="@+id/button1"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="check" 
            android:gravity="center_vertical|center_horizontal"/>
    </LinearLayout>

</ScrollView>
ProgDevCode
la source
1
Cela résout le problème de coupe du haut. Mais il y a encore un problème avec cette solution. Le contenu ScrollView n'était pas centré verticalement. Mais cela peut être résolu en définissant les valeurs suivantes de ScrollView: android: layout_height = "wrap_content" android: layout_gravity = "center_vertical"
Patrick Boos
J'ai trouvé que pour que cela fonctionne dans d'autres mises en page, le ScrollView supérieur doit être intégré dans un FrameLayout.
Theo
1

Une chose à considérer est ce qu'il ne faut PAS définir . Assurez-vous que vos contrôles enfants, en particulier les EditTextcontrôles, n'ont pas la RequestFocuspropriété définie.

Cela peut être l'une des dernières propriétés interprétées sur la mise en page et il remplacera les paramètres de gravité sur ses parents ( layoutou ScrollView).

Epsilon3
la source
0

en utilisant la vue de défilement à l'intérieur du ConstraintLayout. Ça a marché pour moi

<androidx.constraintlayout.widget.ConstraintLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:background="@android:color/white">

            <ScrollView
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                app:layout_constraintBottom_toBottomOf="parent"
                app:layout_constraintEnd_toEndOf="parent"
                app:layout_constraintStart_toStartOf="parent"
                app:layout_constraintTop_toTopOf="parent">

                <LinearLayout
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:orientation="vertical" />
            </ScrollView>
        </androidx.constraintlayout.widget.ConstraintLayout>

La hauteur de la vue de défilement doit être wrap_content

<ScrollView
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
Hariharan Kanakaraja
la source