150

I'm trying to add a ProgressBar on top of a Button (both are inside a ConstraintLayout).

<Button
    android:id="@+id/sign_in_button"
    android:layout_width="280dp"
    android:layout_height="75dp"
    android:layout_marginBottom="75dp"
    android:layout_marginTop="50dp"
    android:text="@string/sign_in"
    android:textColor="@color/white"
    android:textSize="22sp"
    android:textStyle="bold"
    app:layout_constraintBottom_toBottomOf="parent"
    app:layout_constraintLeft_toLeftOf="parent"
    app:layout_constraintRight_toRightOf="parent"
    app:layout_constraintTop_toBottomOf="@+id/passwordEditText"
    app:layout_constraintVertical_bias="0.0"/>

<ProgressBar
    android:id="@+id/progressBar"
    style="?android:attr/progressBarStyle"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    app:layout_constraintTop_toTopOf="@+id/sign_in_button"
    android:layout_marginTop="8dp"
    app:layout_constraintBottom_toBottomOf="@+id/sign_in_button"
    android:layout_marginBottom="8dp"
    app:layout_constraintVertical_bias="0.5"
    android:layout_marginLeft="8dp"
    app:layout_constraintLeft_toLeftOf="@+id/sign_in_button"
    android:layout_marginRight="8dp"
    app:layout_constraintRight_toRightOf="@+id/sign_in_button"/>

But even after calling bringToFront on the ProgressBar in onCreate, it always stays behind the Button.

ProgressBar progressBar = (ProgressBar)findViewById(R.id.progressBar);
progressBar.bringToFront();
Cheticamp
  • 61,413
  • 10
  • 78
  • 131
Adam Johns
  • 35,397
  • 25
  • 123
  • 176
  • this is so weird, I tried to play a bit with your layout, even inverting the chain so that the progress bar is constraint to the edit text and the button to the progress bar but the button seems to be always on top of the progress bar – lelloman Jun 04 '17 at 06:53
  • Are you able to use a FrameLayout ? Give it a try, knowing that in FrameLayout, the z-index is given by the order inside the layout ( so Button 1st, Progress 2nd ) – razgraf Jun 04 '17 at 07:27
  • where is your passwordEditText as i checked without app:layout_constraintTop_toBottomOf="@+id/passwordEditText" i can see progress bar on top can u provide that passwordEditText – Pavan Jun 04 '17 at 08:08

8 Answers8

249

Set an elevation on the ProgressBar; 2dp seems to work.

android:elevation="2dp"

You could also try setting translationZ as suggested in the accepted answer to a similar question.

I also came across this answer as an alternative.

Cheticamp
  • 61,413
  • 10
  • 78
  • 131
27

We need to use android:elevation to control this.

android:elevation="10dp"

This elevation attribute only work in API level >= 21. But In below that it will behave normally. If we add Progress below the Button view it show the view which is in the bottom at the top of the other view.

ThomasW
  • 16,981
  • 4
  • 79
  • 106
Ishan Fernando
  • 2,758
  • 1
  • 31
  • 38
13

You can simply define the view which you want on top after the one which should appear below it.

With buttons, note that their elevation is governed by their stateListAnimator. The stateListAnimator of Widget.MaterialComponents.Button has a default elevation of @dimen/mtrl_btn_elevation (2dp). So if you want to show a view on top of a Button, it should have an elevation of at least 2dp.

Cristan
  • 12,083
  • 7
  • 65
  • 69
7

In Constraint layout you should use

traslationz

higher than view that you want to below .

Waqas Yousaf
  • 264
  • 4
  • 13
5

Although android:elevation="4dp" or traslationz will work, but for that API level should at least 21. If for some reason you can't do that, make sure the view you want on top is mentioned after other views. For example, if I want progressBar on top of ImageView:

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout 
   xmlns:android="http://schemas.android.com/apk/res/android"
   xmlns:app="http://schemas.android.com/apk/res-auto"
   xmlns:tools="http://schemas.android.com/tools"
   android:layout_width="match_parent"
   android:layout_height="match_parent"
   tools:context=".ImageActivity">

<ImageView
   android:id="@+id/image_view"
   android:layout_width="0dp"
   android:layout_height="0dp"
   app:layout_constraintBottom_toBottomOf="parent"
   app:layout_constraintDimensionRatio="6:4"
   app:layout_constraintEnd_toEndOf="parent"
   app:layout_constraintStart_toStartOf="parent"
   app:layout_constraintTop_toTopOf="parent" />

<ProgressBar
   android:id="@+id/progress_bar"
   style="?android:attr/progressBarStyle"
   android:layout_width="wrap_content"
   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" />
</androidx.constraintlayout.widget.ConstraintLayout>
Abhi
  • 2,115
  • 2
  • 18
  • 29
2

Using elevation is working but it has some limitations like it requires api level 21+ and also if elevation is less(in my case it was 2dp) then view become invisible while doing long click therefore you can use a trick simply replace button with "View" or "TextView" you can do everything with these views which can be done with buttonView

PRANAV SINGH
  • 1,000
  • 11
  • 17
1

Updated answer for Android Sutdio 3.5:

In the updated Layout Editor it's now much easier to choose which View will be in front as demonstrated in the Android Studio release notes

.. In addition, a blue overlay now highlights the target of the constraint. This highlighting is particularly useful when attempting to constrain to a component that overlaps with another.

https://developer.android.com/studio/releases

Even easier, If you drag the View up (copy paste or from the Component Tree in the layout editor) it will get lower priority (so it will be behind the other views)

Refael
  • 11
  • 2
1

Button by default have TranslationZ set , so you have two options

1 - make progress bar TranslationZ greater than button elevation

ViewCompat.setTranslationZ(progressBar, 5)// to support older api <21

2 - make button TranslateZ to 0 so the views Appear above each other in order in your Constraint Layout , you can achieve this by Setting Style to button

style="@style/Widget.AppCompat.Button.Borderless"
Mohammed Alaa
  • 3,140
  • 2
  • 19
  • 21