Je souhaite afficher une superposition sur l'écran qui affiche un petit symbole de chargement ou éventuellement du texte pendant que mon application tente de se connecter au serveur. Mon écran de connexion est tout à l'intérieur d'une disposition linéaire verticale.
L’effet que j’essaie d’obtenir ressemble à ceci: http://docs.xamarin.com/recipes/ios/standard_controls/popovers/display_a_loading_message
Peut-être trop tard, mais je suppose que quelqu'un pourrait le trouver utile.
Activité:
public class MainActivity extends Activity implements View.OnClickListener {
String myLog = "myLog";
AlphaAnimation inAnimation;
AlphaAnimation outAnimation;
FrameLayout progressBarHolder;
Button button;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
button = (Button) findViewById(R.id.button);
progressBarHolder = (FrameLayout) findViewById(R.id.progressBarHolder);
button.setOnClickListener(this);
}
@Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.button:
new MyTask().execute();
break;
}
}
private class MyTask extends AsyncTask <Void, Void, Void> {
@Override
protected void onPreExecute() {
super.onPreExecute();
button.setEnabled(false);
inAnimation = new AlphaAnimation(0f, 1f);
inAnimation.setDuration(200);
progressBarHolder.setAnimation(inAnimation);
progressBarHolder.setVisibility(View.VISIBLE);
}
@Override
protected void onPostExecute(Void aVoid) {
super.onPostExecute(aVoid);
outAnimation = new AlphaAnimation(1f, 0f);
outAnimation.setDuration(200);
progressBarHolder.setAnimation(outAnimation);
progressBarHolder.setVisibility(View.GONE);
button.setEnabled(true);
}
@Override
protected Void doInBackground(Void... params) {
try {
for (int i = 0; i < 5; i++) {
Log.d(myLog, "Emulating some task.. Step " + i);
TimeUnit.SECONDS.sleep(1);
}
} catch (InterruptedException e) {
e.printStackTrace();
}
return null;
}
}
}
Layout xml:
<RelativeLayout xmlns:Android="http://schemas.Android.com/apk/res/Android"
xmlns:tools="http://schemas.Android.com/tools"
Android:layout_width="match_parent"
Android:layout_height="match_parent"
tools:context=".MainActivity">
<Button
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:text="Start doing stuff"
Android:id="@+id/button"
Android:layout_below="@+id/textView"
Android:layout_centerHorizontal="true" />
<TextView
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:textAppearance="?android:attr/textAppearanceLarge"
Android:text="Do Some Stuff"
Android:id="@+id/textView"
Android:layout_alignParentTop="true"
Android:layout_centerHorizontal="true" />
<FrameLayout
Android:id="@+id/progressBarHolder"
Android:animateLayoutChanges="true"
Android:visibility="gone"
Android:alpha="0.4"
Android:background="#000000"
Android:layout_width="match_parent"
Android:layout_height="match_parent">
<ProgressBar
style="?android:attr/progressBarStyleLarge"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:indeterminate="true"
Android:layout_gravity="center" />
</FrameLayout>
</RelativeLayout>
J'aime l'approche de Kostya Mais la réponse .
Sur cette base, voici quelques idées pour créer facilement la même superposition réutilisable dans votre application:
Envisagez de placer FrameLayout en superposition dans un fichier de présentation séparé, par exemple. res/layout/include_progress_overlay
:
<FrameLayout
xmlns:Android="http://schemas.Android.com/apk/res/Android"
Android:id="@+id/progress_overlay"
Android:layout_width="match_parent"
Android:layout_height="match_parent"
Android:alpha="0.4"
Android:animateLayoutChanges="true"
Android:background="@Android:color/black"
Android:clickable="true"
Android:visibility="gone">
<ProgressBar
style="?android:attr/progressBarStyleLarge"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_gravity="center"
Android:indeterminate="true"/>
</FrameLayout>
(Une chose que j'ai ajoutée dans la superposition FrameLayout est Android:clickable="true"
. Ainsi, si la superposition est affichée, elle empêche les clics d'atteindre les éléments de l'interface utilisateur situés en dessous. Au moins, dans mon cas d'utilisation typique, c'est ce que je veux.)
Ensuite, incluez-le si nécessaire:
<!-- Progress bar overlay; shown while login is in progress -->
<include layout="@layout/include_progress_overlay"/>
Et en code:
View progressOverlay;
[...]
progressOverlay = findViewById(R.id.progress_overlay);
[...]
// Show progress overlay (with animation):
AndroidUtils.animateView(progressOverlay, View.VISIBLE, 0.4f, 200);
[...]
// Hide it (with animation):
AndroidUtils.animateView(progressOverlay, View.GONE, 0, 200);
Avec le code d'animation extrait dans une méthode util:
/**
* @param view View to animate
* @param toVisibility Visibility at the end of animation
* @param toAlpha Alpha at the end of animation
* @param duration Animation duration in ms
*/
public static void animateView(final View view, final int toVisibility, float toAlpha, int duration) {
boolean show = toVisibility == View.VISIBLE;
if (show) {
view.setAlpha(0);
}
view.setVisibility(View.VISIBLE);
view.animate()
.setDuration(duration)
.alpha(show ? toAlpha : 0)
.setListener(new AnimatorListenerAdapter() {
@Override
public void onAnimationEnd(Animator animation) {
view.setVisibility(toVisibility);
}
});
}
(Ici, en utilisant view.animate()
, ajouté dans l’API 12, au lieu de AlphaAnimation
.)
J'ai ProgressBar dans Relative Layout et je le cache ou le montre respectivement. Et oui l'activité peut être transparente.
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:Android="http://schemas.Android.com/apk/res/Android"
Android:layout_width="match_parent"
Android:layout_height="match_parent" >
<LinearLayout
Android:id="@+id/hsvBackgroundContainer"
Android:layout_width="match_parent"
Android:layout_height="match_parent"
Android:layout_alignParentLeft="true"
Android:layout_alignParentTop="true"
</LinearLayout>
<ProgressBar
Android:id="@+id/pbProgess"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_centerHorizontal="true"
Android:layout_centerVertical="true" />
</RelativeLayout>
Un spinner avec un message sur l'application peut être créé à l'aide de ProgressDialog. Bien que cela ne produise pas l'effet exact comme dans l'image, c'est un bon moyen de montrer que l'application fonctionne.
J'ai eu la même question, j'ai essayé les solutions mais n'était pas la meilleure interface utilisateur, donc, j'ai fait les étapes suivantes.
content.background = "# 000000" content.alpha = "0.4"
<FrameLayout
xmlns:Android="http://schemas.Android.com/apk/res/Android"
xmlns:tools="http://schemas.Android.com/tools"
Android:layout_width="match_parent"
Android:layout_height="match_parent">
<RelativeLayout
Android:id="@+id/content"
Android:layout_width="match_parent"
Android:layout_height="match_parent"
Android:animateLayoutChanges="true"
tools:context=".MainActivity">
<Button
Android:id="@+id/button"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_below="@+id/textView"
Android:layout_centerHorizontal="true"
Android:text="Start doing stuff" />
<TextView
Android:id="@+id/textView"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_alignParentTop="true"
Android:layout_centerHorizontal="true"
Android:text="Do Some Stuff"
Android:textAppearance="?android:attr/textAppearanceLarge" />
</RelativeLayout>
<ProgressBar
style="?android:attr/progressBarStyleLarge"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_gravity="center"
Android:indeterminate="true"
Android:visibility="gone" />
</FrameLayout>