Esempio FloatingActionButton con Support Library


129

Di recente, ho letto questi post:

Libreria di supporto per la progettazione Android

Libreria di supporto Android, revisione 22.2.0

FloatingActionButton

Ma nessuno di loro mi dà un esempio dettagliato sulla creazione di un nuovo FloatingActionButton. Così difficile da capire, faccio questa domanda.

Qualcuno può darmi un esempio al riguardo?

Qualsiasi aiuto è molto apprezzato. Grazie in anticipo.

MODIFICARE

Ho appena riscontrato alcuni problemi su FloatingActionButton(FAB) e voglio migliorare un'altra risposta. Vedi la mia risposta qui sotto.


Risposte:


274

Quindi nel tuo build.gradlefile, aggiungi questo:

compile 'com.android.support:design:27.1.1'

Nota AndroidX: Google sta introducendo nuove librerie di estensioni AndroidX per sostituire le librerie di supporto precedenti. Per usare AndroidX, assicurati innanzitutto di aver aggiornato il tuo gradle.propertiesfile , modificato build.gradleper impostarlo compileSdkVersionsu 28(o superiore) e usa la seguente riga invece di quella precedente compile.

implementation 'com.google.android.material:material:1.0.0'

Successivamente, nel tuo themes.xmlo styles.xmlqualsiasi altra cosa, assicurati di impostare questo - è il colore dell'accento della tua app - e il colore del tuo FAB a meno che tu non lo ignori (vedi sotto):

        <item name="colorAccent">@color/floating_action_button_color</item>

Nell'XML del layout:

<RelativeLayout
 ...
 xmlns:app="http://schemas.android.com/apk/res-auto">

       <android.support.design.widget.FloatingActionButton
            android:id="@+id/myFAB"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:src="@drawable/ic_plus_sign"
            app:elevation="4dp"
            ... />

</RelativeLayout>

O se stai usando la libreria di materiali AndroidX sopra, dovresti invece usare questo:

<RelativeLayout
 ...
 xmlns:app="http://schemas.android.com/apk/res-auto">

       <com.google.android.material.floatingactionbutton.FloatingActionButton
            android:id="@+id/myFAB"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:srcCompat="@drawable/ic_plus_sign"
            app:elevation="4dp"
            ... />

</RelativeLayout>

Puoi vedere più opzioni nei documenti ( documenti materiali qui) ( setRippleColor, ecc.), Ma uno di nota è:

    app:fabSize="mini"

Un altro interessante-- per cambiare il colore di sfondo di un solo FAB, aggiungi:

    app:backgroundTint="#FF0000"

(ad esempio per cambiarlo in rosso) nell'XML sopra.

Ad ogni modo, nel codice, dopo che la vista Attività / Frammento è gonfiata ...

    FloatingActionButton myFab = (FloatingActionButton)  myView.findViewById(R.id.myFAB);
    myFab.setOnClickListener(new View.OnClickListener() {
        public void onClick(View v) {
            doMyThing();
        }
    });

osservazioni:

  • Se hai uno di quei pulsanti su una "cucitura" che divide due viste (usando un RelativeLayout, per esempio) con, diciamo, un margine di layout inferiore negativo per sovrapporre il bordo, noterai un problema: la dimensione del FAB è in realtà molto diverso su lecca-lecca rispetto a pre-lecca-lecca. Puoi effettivamente vederlo nell'editor del layout visivo di AS quando passi da una API all'altra, improvvisamente si gonfia quando passi al pre-lecca-lecca. Il motivo della dimensione aggiuntiva sembra essere che l'ombra espande la dimensione della vista in ogni direzione. Quindi devi tener conto di questo quando modifichi i margini del FAB se è vicino ad altre cose.
  • Ecco un modo per rimuovere o modificare il riempimento se c'è troppo:

    if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
        RelativeLayout.LayoutParams p = (RelativeLayout.LayoutParams) myFab.getLayoutParams();
        p.setMargins(0, 0, 0, 0); // get rid of margins since shadow area is now the margin
        myFab.setLayoutParams(p);
    }
  • Inoltre, avrei programmato di posizionare il FAB sulla "giuntura" tra due aree in un RelayLayout afferrando l'altezza del FAB, dividendolo per due e usandolo come offset del margine. Ma myFab.getHeight () ha restituito zero, anche dopo che la vista è stata gonfiata, sembrava. Invece ho usato un ViewTreeObserver per ottenere l'altezza solo dopo che è stato disposto e quindi impostare la posizione. Vedi questo consiglio qui . Sembrava così:

        ViewTreeObserver viewTreeObserver = closeButton.getViewTreeObserver();
        if (viewTreeObserver.isAlive()) {
            viewTreeObserver.addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
                @Override
                public void onGlobalLayout() {
                    if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
                        closeButton.getViewTreeObserver().removeGlobalOnLayoutListener(this);
                    } else {
                        closeButton.getViewTreeObserver().removeOnGlobalLayoutListener(this);
                    }
                    // not sure the above is equivalent, but that's beside the point for this example...
                    RelativeLayout.LayoutParams params = (RelativeLayout.LayoutParams) closeButton.getLayoutParams();
                    params.setMargins(0, 0, 16, -closeButton.getHeight() / 2); // (int left, int top, int right, int bottom)
                    closeButton.setLayoutParams(params);
                }
            });
        }

    Non sono sicuro se questo è il modo giusto per farlo, ma sembra funzionare.

  • Sembra che puoi ridurre lo spazio ombra del pulsante diminuendo l'elevazione.
  • Se vuoi il FAB su una "cucitura" puoi usare layout_anchored layout_anchorGravityecco un esempio:

    <android.support.design.widget.FloatingActionButton
        android:layout_height="wrap_content"
        android:layout_width="wrap_content"
        app:layout_anchor="@id/appbar"
        app:layout_anchorGravity="bottom|right|end"
        android:src="@drawable/ic_discuss"
        android:layout_margin="@dimen/fab_margin"
        android:clickable="true"/>

Ricorda che puoi far saltare automaticamente il pulsante quando si presenta una Snackbar avvolgendola in un CoordinatorLayout .

Di Più:


1
Sicuro. Aggiungi android:backgroundTint="#FF0000"ad esempio a FloatingActionBar nell'XML. (aggiungendo per rispondere)
ingrasso

1
Hmm. Va bene lo cambierò sopra allora. Grazie! Dark Leonhart-- Non ho visto nulla del ritorno rapido incorporato ma ci sono esempi di farlo altrove su StackOver che presumo funzionerà ancora. Inoltre sono disponibili alcune librerie che lo fanno anche.
ingrasso

1
Questo componente, a partire dal 22.2.0, secondo me, non è pronto per la produzione. A proposito, potrebbe essere un errore di battitura, ma non utilizzare spnella proprietà evelation. Dovrebbe essereapp:elevation="4dp"
Joao Sousa il

1
Nota se stai aggiungendo a FloatingActionButtona CoordinatorLayout, puoi usare app:layout_anchor="element_with_seam"e app:layout_anchorGravity="bottom|right|end"posizionare correttamente il FAB su una cucitura - vedi il layout activity_detail da cheesesquare
ianhanniballake

2
@DarkLeonhart - guarda il mio esempio di mostrare / nascondere il FAB su scroll estendendone il comportamento.
ianhanniballake,

49

Ho appena riscontrato alcuni problemi su FAB e voglio migliorare un'altra risposta.


problema setRippleColor

Quindi, il problema si presenterà dopo aver impostato il colore dell'ondulazione (colore FAB su premuto) a livello di codice setRippleColor. Ma abbiamo ancora un modo alternativo per impostarlo, cioè chiamando:

FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
ColorStateList rippleColor = ContextCompat.getColorStateList(context, R.color.fab_ripple_color);
fab.setBackgroundTintList(rippleColor);

Il tuo progetto deve avere questa struttura:

/res/color/fab_ripple_color.xml

inserisci qui la descrizione dell'immagine

E il codice da fab_ripple_color.xmlè:

<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_pressed="true" android:color="@color/fab_color_pressed" />
    <item android:state_focused="true" android:color="@color/fab_color_pressed" />
    <item android:color="@color/fab_color_normal"/>
</selector>

Infine, modifica leggermente il tuo FAB:

<android.support.design.widget.FloatingActionButton
    android:id="@+id/fab"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:src="@drawable/ic_action_add"
    android:layout_alignParentBottom="true"
    android:layout_alignParentRight="true"
    app:fabSize="normal"
    app:borderWidth="0dp"
    app:elevation="6dp"
    app:pressedTranslationZ="12dp"
    app:rippleColor="@android:color/transparent"/> <!-- set to transparent color -->

Per API di livello 21 e superiore, imposta il margine destro e inferiore su 24dp:

...
android:layout_marginRight="24dp"
android:layout_marginBottom="24dp" />

Guide alla progettazione di FloatingActionButton

Come puoi vedere sul mio codice XML FAB sopra, ho impostato:

        ...
        android:layout_alignParentBottom="true"
        android:layout_alignParentRight="true"
        app:elevation="6dp"
        app:pressedTranslationZ="12dp"
        ...
  • Impostando questi attributi, non è necessario impostare layout_marginTope di layout_marginRightnuovo (solo su pre-Lollipop). Android lo posizionerà automaticamente sul lato destro dello schermo, lo stesso del normale FAB in Android Lollipop.

        android:layout_alignParentBottom="true"
        android:layout_alignParentRight="true"

Oppure puoi usare questo in CoordinatorLayout:

        android:layout_gravity="end|bottom"
  • Devi avere 6dp elevatione 12dp pressedTranslationZ, secondo questa guida di Google.

Regole FAB


5
pollice in alto per la ricerca coinvolta. più 1 per il pressedTranslationZ. Non lo sapevo.
Joao Sousa,

app: elevation = "6dp" app: premutoTranslationZ = "12dp" fa il trucco per il pre-lecca lecca, ma il mio fab è letteralmente all'angolo dello schermo su Lollipop
Thiago

1
Stai utilizzando un valore errato per "premutoTranslationZ". Non è il valore dell'elevazione su stato premuto. PressedElevation = elevazione + premutoTranslationZ. Quindi i valori corretti sono app: elevazione = "6dp" app: premutoTranslationZ = "6dp"
e.shishkin

3
In realtà non è necessario impostare i valori app:elevatione app:pressedTranslationZ. Il loro valore predefinito è quello definito nelle linee guida per la progettazione dei materiali. Ad ogni modo, e.shishkin ha ragione, i valori sono app:elevation:6dpe pressedTranslationZ:6dp. Puoi verificarlo nel codice sorgente
Christian García,

12

FloatingActionButtonsi estende ImageView. Quindi, è semplice come introdurre un ImageViewlayout. Ecco un esempio XML.

<android.support.design.widget.FloatingActionButton   xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/fab"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:src="@drawable/somedrawable"
    android:layout_gravity="right|bottom"
    app:borderWidth="0dp"
    app:rippleColor="#ffffff"/>

app:borderWidth="0dp" viene aggiunto come soluzione alternativa per problemi di elevazione.


4

per AndroidX usare come

<com.google.android.material.floatingactionbutton.FloatingActionButton
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    app:srcCompat="@drawable/ic_add" />

1

Se hai già aggiunto tutte le librerie e non funziona ancora, usa:

<com.google.android.material.floatingactionbutton.FloatingActionButton
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    app:srcCompat="@drawable/ic_add" 
/>

invece di:

<android.support.design.widget.FloatingActionButton
   android:layout_width="wrap_content"
   android:layout_height="wrap_content"
   app:srcCompat="@drawable/ic_add"
 />

E tutto funzionerà bene :)

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.