欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

Android自定义Dialog原理实例解析

程序员文章站 2022-04-05 18:52:35
android开发过程中,常常会遇到一些需求场景——在界面上弹出一个弹框,对用户进行提醒并让用户进行某些选择性的操作,如退出登录时的弹窗,让用户选择“退出”还是“取消”等操作。android系统提供了...

android开发过程中,常常会遇到一些需求场景——在界面上弹出一个弹框,对用户进行提醒并让用户进行某些选择性的操作,

如退出登录时的弹窗,让用户选择“退出”还是“取消”等操作。

android系统提供了dialog类,以及dialog的子类,常见如alertdialog来实现此类功能。

一般情况下,利用android提供的dialog及其子类能够满足多数此类需求,然而,其不足之处体现在:

1. 基于android提供的dialog及其子类样式单一,风格上与app本身风格可能不太协调;

2. dialog弹窗在布局和功能上有所限制,有时不一定能满足实际的业务需求。

本文将通过在dialog基础上构建自定义的dialog弹窗,以最常见的确认弹框为例。

本样式相对比较简单:上面有一个弹框标题(提示语),下面左右分别是“确认”和“取消”按钮,当用户点击“确认”按钮时,弹框执行

相应的确认逻辑,当点击“取消”按钮时,执行相应的取消逻辑。

首先,自定义弹框样式:

<?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:background="@drawable/dialog_bg"
  android:orientation="vertical" >

  <textview
    android:id="@+id/title"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_gravity="center"
    android:paddingtop="14dp"
    android:textcolor="@color/login_hint"
    android:textsize="@dimen/text_size_18" />

  <linearlayout
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_marginbottom="14dp"
    android:layout_marginleft="20dp"
    android:layout_marginright="20dp"
    android:layout_margintop="30dp" >

    <textview
      android:id="@+id/confirm"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:layout_marginright="10dp"
      android:layout_weight="1"
      android:background="@drawable/btn_confirm_selector"
      android:gravity="center"
      android:textcolor="@color/white"
      android:textsize="@dimen/text_size_16" />

    <textview
      android:id="@+id/cancel"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:layout_marginleft="10dp"
      android:layout_weight="1"
      android:background="@drawable/btn_cancel_selector"
      android:gravity="center"
      android:textcolor="@color/login_hint"
      android:textsize="@dimen/text_size_16" />
  </linearlayout>

</linearlayout>

然后,通过继承dialog类构建确认弹框控件confirmdialog:

package com.corn.widget;

import android.app.dialog;
import android.content.context;
import android.os.bundle;
import android.util.displaymetrics;
import android.view.layoutinflater;
import android.view.view;
import android.view.window;
import android.view.windowmanager;
import android.widget.textview;

import com.corn.r;

public class confirmdialog extends dialog {

  private context context;
  private string title;
  private string confirmbuttontext;
  private string cacelbuttontext;
  private clicklistenerinterface clicklistenerinterface;

  public interface clicklistenerinterface {

    public void doconfirm();

    public void docancel();
  }

  public confirmdialog(context context, string title, string confirmbuttontext, string cacelbuttontext) {
    super(context, r.style.mydialog);
    this.context = context;
    this.title = title;
    this.confirmbuttontext = confirmbuttontext;
    this.cacelbuttontext = cacelbuttontext;
  }

  @override
  protected void oncreate(bundle savedinstancestate) {
    // todo auto-generated method stub
    super.oncreate(savedinstancestate);

    init();
  }

  public void init() {
    layoutinflater inflater = layoutinflater.from(context);
    view view = inflater.inflate(r.layout.confirm_dialog, null);
    setcontentview(view);

    textview tvtitle = (textview) view.findviewbyid(r.id.title);
    textview tvconfirm = (textview) view.findviewbyid(r.id.confirm);
    textview tvcancel = (textview) view.findviewbyid(r.id.cancel);

    tvtitle.settext(title);
    tvconfirm.settext(confirmbuttontext);
    tvcancel.settext(cacelbuttontext);

    tvconfirm.setonclicklistener(new clicklistener());
    tvcancel.setonclicklistener(new clicklistener());

    window dialogwindow = getwindow();
    windowmanager.layoutparams lp = dialogwindow.getattributes();
    displaymetrics d = context.getresources().getdisplaymetrics(); // 获取屏幕宽、高用
    lp.width = (int) (d.widthpixels * 0.8); // 高度设置为屏幕的0.6
    dialogwindow.setattributes(lp);
  }

  public void setclicklistener(clicklistenerinterface clicklistenerinterface) {
    this.clicklistenerinterface = clicklistenerinterface;
  }

  private class clicklistener implements view.onclicklistener {
    @override
    public void onclick(view v) {
      // todo auto-generated method stub
      int id = v.getid();
      switch (id) {
      case r.id.confirm:
        clicklistenerinterface.doconfirm();
        break;
      case r.id.cancel:
        clicklistenerinterface.docancel();
        break;
      }
    }

  };

}

在如上空间构造代码中,由于控件的"确认"和"取消"逻辑与实际的应用场景有关,因此,控件中通过定义内部接口来实现。

在需要使用此控件的地方,进行如下形式调用:

public static void exit(final context context) {
    final confirmdialog confirmdialog = new confirmdialog(context, "确定要退出吗?", "退出", "取消");
    confirmdialog.show();
    confirmdialog.setclicklistener(new confirmdialog.clicklistenerinterface() {
      @override
      public void doconfirm() {
        // todo auto-generated method stub
        confirmdialog.dismiss();
        //touserhome(context);
        appmanager.getappmanager().appexit(context);
      }

      @override
      public void docancel() {
        // todo auto-generated method stub
        confirmdialog.dismiss();
      }
    });
  }

调用中实现了此控件的内部接口,并赋给控件本身,以此在点击按钮时实现基于外部具体业务逻辑的函数回调。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。