English | 简体中文 | 繁體中文 | Русский язык | Français | Español | Português | Deutsch | 日本語 | 한국어 | Italiano | بالعربية

Android Control PopupWindow imita la ventana emergente inferior de iOS

Prólogo

En H5En la era ferviente, muchos marcos han lanzado controles de ventana emergente inferior, en H5Conocido como ActionSheet emergente, hoy también imitamos una ventana emergente inferior de iOS, inspirada en la función de seleccionar avatar de Apple QQ.

Texto principal

Sin más preámbulos, primero muestro la imagen del efecto que vamos a implementar hoy


Todo el código de apertura de PopupWindow

private void openPopupWindow(View v) {
  //evitarClicRepetidoBoton
  if (popupWindow != null && popupWindow.isShowing()) {
    return;
  }
  //establecerViewPopupWindow
  View view = LayoutInflater.from(this).inflate(R.layout.view_popupwindow, null);
  popupWindow = new PopupWindow(view, RelativeLayout.LayoutParams.MATCH_PARENT,
      RelativeLayout.LayoutParams.WRAP_CONTENT);
  //establecerFondo, esto no tiene mucho efecto, no agregarlo generará un error
  popupWindow.setBackgroundDrawable(new BitmapDrawable());
  //ocultarPropioAlClicFuera
  popupWindow.setFocusable(true);
  popupWindow.setOutsideTouchable(true);
  //establecerAnimacion
  popupWindow.setAnimationStyle(R.style.PopupWindow);
  //establecerPosicion
  popupWindow.showAtLocation(v, Gravity.BOTTOM, 0, navigationHeight);
  //establecerEscuchaDesaparecer
  popupWindow.setOnDismissListener(this);
  //establecerEventoClicViewPopupWindow
  setOnPopupViewClick(view);
  //establecerColorFondo
  setBackgroundAlpha(0.5f);
}

Análisis de pasos:

La disposición de PopupWindow
Crear PopupWindow
Agregar efectos de animación a PopupWindow
Configurar la sombra de fondo de PopupWindow
Escuchar eventos de clic en PopupWindow
Obtener la altura de la barra de navegación inferior

La disposición de PopupWindow: En el Layout, diseñamos la disposición necesaria

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical">
  <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_margin="8dp" android:background="@drawable/popup_shape" android:orientation="vertical">
    <TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:gravity="center" android:padding="16dp" android:text="Puede subir fotos a la pared de fotos" android:textColor="#666" android:textSize="14sp" />
    <View android:layout_width="match_parent" android:layout_height="0.1px" android:background="#888" />
    <TextView android:id="@+id/tv_pick_phone" android:layout_width="match_parent" android:layout_height="wrap_content" android:gravity="center" android:padding="16dp" android:text="Elija fotos de la galería del teléfono" android:textColor="#118" android:textSize="18sp" />
    <View android:layout_width="match_parent" android:layout_height="0.1px" android:background="#888" />
    <TextView android:id="@+id/tv_pick_zone" android:layout_width="match_parent" android:layout_height="wrap_content" android:gravity="center" android:padding="16dp" android:text="Elija fotos de la galería del espacio" android:textColor="#118" android:textSize="18sp" />
  </LinearLayout>
  <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_margin="8dp" android:background="@drawable/popup_shape">
    <TextView android:id="@+id/tv_cancel" android:layout_width="match_parent" android:layout_height="wrap_content" android:gravity="center" android:padding="16dp" android:text="Cancelar" android:textColor="#118" android:textSize="18sp" android:textStyle="bold" />
  </LinearLayout>
</LinearLayout>

Su efecto es:


Creación de PopupWindow: Esta creación es igual a la de nuestros componentes comunes

//establecerViewPopupWindow
View view = LayoutInflater.from(this).inflate(R.layout.view_popupwindow, null);
popupWindow = new PopupWindow(view, RelativeLayout.LayoutParams.MATCH_PARENT,
        RelativeLayout.LayoutParams.WRAP_CONTENT);

Agregar efecto de animación a PopupWindow: Creemos una carpeta anim, creamos nuestros efectos de animación out e in, luego agregamos nuestras animaciones en style

<?xml version="1.0" encoding="utf-8"?>
!--Animación de entrada-->
<translate xmlns:android="http://schemas.android.com/apk/res/android" android:interpolator="@android:anim/accelerate_interpolator" android:fromYDelta="100%" android:toYDelta="0" android:duration="200"/>
<?xml version="1.0" encoding="utf-8"?>
!--Animación de salida-->
<translate xmlns:android="http://schemas.android.com/apk/res/android" android:interpolator="@android:anim/accelerate_interpolator" android:fromYDelta="0" android:toYDelta="100%" android:duration="200"/>
!--Animación de ventana emergente-->
<style name="PopupWindow"> <item name="android:windowEnterAnimation">@anim/window_in</item> <item name="android:windowExitAnimation">@anim/window_out</item> </style>

//establecerAnimacion
popupWindow.setAnimationStyle(R.style.PopupWindow);

Configurar la sombra de fondo de PopupWindow: Al abrir la ventana emergente, configure la opacidad a 0.5, al desaparecer la ventana emergente, configure la opacidad a1

//Establecer el efecto de transparencia del fondo de la pantalla
public void setBackgroundAlpha(float alpha) {
  WindowManager.LayoutParams lp = getWindow().getAttributes();
  lp.alpha = alpha;
  getWindow().setAttributes(lp);
}

Escuchar eventos de clic en PopupWindow: Escuchar eventos de clic en los componentes dentro de nuestro PopupWindow

//establecerEventoClicViewPopupWindow
setOnPopupViewClick(view);
private void setOnPopupViewClick(View view) {
  TextView tv_pick_phone, tv_pick_zone, tv_cancel;
  tv_pick_phone = (TextView) view.findViewById(R.id.tv_pick_phone);
  tv_pick_zone = (TextView) view.findViewById(R.id.tv_pick_zone);
  tv_cancel = (TextView) view.findViewById(R.id.tv_cancel);
  tv_pick_phone.setOnClickListener(this);
  tv_pick_zone.setOnClickListener(this);
  tv_cancel.setOnClickListener(this);
}

Obtener la altura de NavigationBar: Aquí se necesita adaptar a algunos teléfonos que no tienen NavigationBar y a algunos que tienen, aquí se demuestra con NavigationBar existente
int resourceId = getResources().getIdentifier("navigation_bar_height", "dimen", "android");
navigationHeight = getResources().getDimensionPixelSize(resourceId);

En los teléfonos con NavigationBar, configure la posición de aparición de PopupWindow
//establecerPosicion
popupWindow.showAtLocation(v, Gravity.BOTTOM, 0, navigationHeight);

En los teléfonos sin NavigationBar, configure la posición de aparición de PopupWindow
//establecerPosicion
popupWindow.showAtLocation(v, Gravity.BOTTOM, 0, 0);

源码

Github:https://github.com/AndroidHensen/IOSPopupWindow

public class MainActivity extends AppCompatActivity implements View.OnClickListener, PopupWindow.OnDismissListener {
  private Button bt_open;
  private PopupWindow popupWindow;
  private int navigationHeight;
  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    bt_open = (Button) findViewById(R.id.bt_open);
    bt_open.setOnClickListener(this);
    int resourceId = getResources().getIdentifier("navigation_bar_height", "dimen", "android");
    navigationHeight = getResources().getDimensionPixelSize(resourceId);
  }
  @Override
  public void onClick(View v) {
    switch (v.getId()) {
      case R.id.bt_open:
        openPopupWindow(v);
        romper;
      case R.id.tv_pick_phone:
        Toast.makeText(this, "从手机相册选择", Toast.LENGTH_SHORT).show();
        popupWindow.dismiss();
        romper;
      case R.id.tv_pick_zone:
        Toast.makeText(this, "从空间相册选择", Toast.LENGTH_SHORT).show();
        popupWindow.dismiss();
        romper;
      case R.id.tv_cancel:
        popupWindow.dismiss();
        romper;
    }
  }
  private void openPopupWindow(View v) {
    //evitarClicRepetidoBoton
    if (popupWindow != null && popupWindow.isShowing()) {
      return;
    }
    //establecerViewPopupWindow
    View view = LayoutInflater.from(this).inflate(R.layout.view_popupwindow, null);
    popupWindow = new PopupWindow(view, RelativeLayout.LayoutParams.MATCH_PARENT,
        RelativeLayout.LayoutParams.WRAP_CONTENT);
    //establecerFondo, esto no tiene mucho efecto, no agregarlo generará un error
    popupWindow.setBackgroundDrawable(new BitmapDrawable());
    //ocultarPropioAlClicFuera
    popupWindow.setFocusable(true);
    popupWindow.setOutsideTouchable(true);
    //establecerAnimacion
    popupWindow.setAnimationStyle(R.style.PopupWindow);
    //establecerPosicion
    popupWindow.showAtLocation(v, Gravity.BOTTOM, 0, navigationHeight);
    //establecerEscuchaDesaparecer
    popupWindow.setOnDismissListener(this);
    //establecerEventoClicViewPopupWindow
    setOnPopupViewClick(view);
    //establecerColorFondo
    setBackgroundAlpha(0.5f);
  }
  private void setOnPopupViewClick(View view) {
    TextView tv_pick_phone, tv_pick_zone, tv_cancel;
    tv_pick_phone = (TextView) view.findViewById(R.id.tv_pick_phone);
    tv_pick_zone = (TextView) view.findViewById(R.id.tv_pick_zone);
    tv_cancel = (TextView) view.findViewById(R.id.tv_cancel);
    tv_pick_phone.setOnClickListener(this);
    tv_pick_zone.setOnClickListener(this);
    tv_cancel.setOnClickListener(this);
  }
  //Establecer el efecto de transparencia del fondo de la pantalla
  public void setBackgroundAlpha(float alpha) {
    WindowManager.LayoutParams lp = getWindow().getAttributes();
    lp.alpha = alpha;
    getWindow().setAttributes(lp);
  }
  @Override
  public void onDismiss() {
    setBackgroundAlpha(1);
  }
}

Esto es todo el contenido del artículo, espero que sea útil para su aprendizaje y que todos los demás lo apoyen en el tutorial de gritos.

Declaración: el contenido de este artículo se obtiene de la red, pertenece al autor original, el contenido se contribuye y carga de manera autónoma por los usuarios de Internet, este sitio no posee los derechos de propiedad, no ha sido editado artificialmente y no asume ninguna responsabilidad legal relacionada. Si encuentra contenido sospechoso de copyright, por favor envíe un correo electrónico a: notice#oldtoolbag.com (al enviar un correo electrónico, por favor reemplace # con @) para denunciar y proporcionar evidencia relevante. Una vez verificada, este sitio eliminará inmediatamente el contenido sospechoso de infracción.

Te gustará