Android使用FrameLayout模仿PoppupWindow

自从Android进入7.0之后,使用PoppupWindow是越来越不顺手了,各种问题出现,而且对于很多个性化定义不是很完美,下面是我做了一些小封装的demo,有问题大家提出来一起学习。



废话不多说,直接上代码:

activity_main.xml:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/ll_container"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"></LinearLayout>
custom_poppup_window.xml
<?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="match_parent"
    android:background="#fff"
    android:orientation="vertical">

    <FrameLayout
        android:id="@+id/ll_tab"
        android:layout_width="match_parent"
        android:layout_height="40dp"
        android:orientation="horizontal" ></FrameLayout>

    <View
        android:layout_width="match_parent"
        android:layout_height="1dp"
        android:background="@color/colorPrimary" />

    <FrameLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:background="#fff">
        <!--内容区-->
        <FrameLayout
            android:id="@+id/fl_content"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:background="#fff" />
        <!--遮罩区-->
        <View
            android:id="@+id/mask"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:background="#99000000"
            android:visibility="gone" />
        <!--弹出框-->
        <FrameLayout
            android:id="@+id/fl_pop"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_gravity="left"
            android:background="#fff"
            android:orientation="horizontal"
            android:visibility="gone"></FrameLayout>
    </FrameLayout>
</LinearLayout>

item_pop_view.xml
<?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="#fff"
    android:orientation="horizontal">

    <ListView
        android:id="@+id/lv_city"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_weight="1"
        android:scrollbars="none" />

    <ListView
        android:id="@+id/lv_age"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_weight="1"
        android:scrollbars="none" />
</LinearLayout>

item_tab_view.xml
<?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">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="40dp"
        android:orientation="horizontal">

        <TextView
            android:id="@+id/tv_city"
            android:layout_width="0dp"
            android:layout_height="match_parent"
            android:layout_weight="1"
            android:drawableRight="@mipmap/icon_to_down"
            android:gravity="center"
            android:paddingLeft="20dp"
            android:paddingRight="20dp"
            android:text="城市" />

        <View
            android:layout_width="1dp"
            android:layout_height="match_parent"
            android:background="@color/colorPrimary" />

        <TextView
            android:id="@+id/tv_age"
            android:layout_width="0dp"
            android:layout_height="match_parent"
            android:layout_weight="1"
            android:drawableRight="@mipmap/icon_to_down"
            android:gravity="center"
            android:paddingLeft="20dp"
            android:paddingRight="20dp"
            android:text="年龄" />
    </LinearLayout>
</LinearLayout>

MainActivity.java:

public class MainActivity extends AppCompatActivity {
    private String content[];
    private String citys[] = {"北京", "上海", "广州", "深圳"};
    private String ages[] = {"1-5", "6-10", "11-15", "16-20"};

 
 
//父布局容器,即Activity中最外层容器
    private LinearLayout ll_container;
    //封装的popupWindow布局
    private CustomPopupWindow popupWindow;
 
 
//对话框的内容容器
private FrameLayout popView;
 
 
//正文内容容器
private FrameLayout contentView;
 
 
//顶部条件筛选栏容器
private FrameLayout tabView;
 
 
//对话框的详细布局
private View viewPop;
 
 
//条件筛选详细布局
private View viewTab; private TextView tvCity; private TextView tvAge; private ListView lvCity; private ListView lvAge;
 
 
//内容列表
private ListView lvContent; /** * 当前展开位置下标 */ private int currentPos = -1; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); initView(); initEvent(); } private void initView() { ll_container = this.findViewById(R.id.ll_container); popupWindow = new CustomPopupWindow(this, ll_container); popView = popupWindow.getPopupView(); contentView = popupWindow.getContentView(); tabView = popupWindow.getTabView(); viewPop = LayoutInflater.from(this).inflate(R.layout.item_pop_view, null); viewTab = LayoutInflater.from(this).inflate(R.layout.item_tab_view, null); popView.addView(viewPop); tabView.addView(viewTab); lvContent = new ListView(this); contentView.addView(lvContent); tvCity = viewTab.findViewById(R.id.tv_city); tvAge = viewTab.findViewById(R.id.tv_age); lvCity = viewPop.findViewById(R.id.lv_city); lvAge = viewPop.findViewById(R.id.lv_age); content = new String[20]; for (int i = 0; i < 20; i++) { content[i] = "第" + (1 + i) + "项"; } ArrayAdapter contentAdapter = new ArrayAdapter<String>(MainActivity.this, android.R.layout.simple_list_item_1, content); lvContent.setAdapter(contentAdapter); //创建数组适配器对象,并且通过参数设置类item项的布局样式和数据源 ArrayAdapter cityAdapter = new ArrayAdapter<String>(MainActivity.this, android.R.layout.simple_list_item_1, citys); //把数组适配器加载到ListView控件中 lvCity.setAdapter(cityAdapter); ArrayAdapter ageAdapter = new ArrayAdapter<String>(MainActivity.this, android.R.layout.simple_list_item_1, ages); //把数组适配器加载到ListView控件中 lvAge.setAdapter(ageAdapter); } private void initEvent() { tvCity.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { if (popupWindow != null) { if (!popupWindow.isShow()) { currentPos = 1; switchPop(); popupWindow.show(); } else { if (currentPos == 2) { currentPos = 1; switchPop(); } else { currentPos = -1; popupWindow.dismiss(); } } } } }); tvAge.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { if (popupWindow != null) { if (!popupWindow.isShow()) { currentPos = 2; switchPop(); popupWindow.show(); } else { if (currentPos == 1) { currentPos = 2; switchPop(); } else { currentPos = -1; popupWindow.dismiss(); } } } } }); } /** * 切换帅选条件 */ private void switchPop() { if (currentPos == 1) { lvCity.setVisibility(View.VISIBLE); lvAge.setVisibility(View.GONE); } else { lvCity.setVisibility(View.GONE); lvAge.setVisibility(View.VISIBLE); } } }
CustomPopupWindow.java:
public class CustomPopupWindow {
    private View pop;

    private Context context;
    /**
     * 标题栏
     */
    private FrameLayout ll_tab;
    /**
     * 内容区域
     */
    private FrameLayout fl_content;
    /**
     * 弹出框区域
     */
    private FrameLayout fl_pop;
    /**
     * 遮罩层区域
     */
    private View mask;
    /**
     * 是否已打开对话框
     */
    private boolean hasOpen = false;

    /**
     * @param context
     * @param parentContainer 最外层父容器
     */
    public CustomPopupWindow(Context context, LinearLayout parentContainer) {
        this.context = context;
        pop = LayoutInflater.from(context).inflate(R.layout.custom_poppup_window, null);
        parentContainer.addView(pop);
        initView();
        initEvent();
    }

    private void initView() {
        ll_tab = pop.findViewById(R.id.ll_tab);
        fl_content = pop.findViewById(R.id.fl_content);
        fl_pop = pop.findViewById(R.id.fl_pop);
        mask = pop.findViewById(R.id.mask);
    }

    private void initEvent() {
        mask.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                dismiss();
            }
        });
    }

    /**
     * 打开对话框
     */
    public void show() {
        if (!hasOpen) {
            fl_pop.setVisibility(View.VISIBLE);
            fl_pop.setAnimation(AnimationUtils.loadAnimation(context, R.anim.add_menu_in));
            mask.setVisibility(View.VISIBLE);
            mask.setAnimation(AnimationUtils.loadAnimation(context, R.anim.add_mask_in));
            hasOpen = true;
        }
    }

    /**
     * 关闭对话框
     */
    public void dismiss() {
        fl_pop.setVisibility(View.GONE);
        fl_pop.setAnimation(AnimationUtils.loadAnimation(context, R.anim.add_menu_out));
        mask.setVisibility(View.GONE);
        mask.setAnimation(AnimationUtils.loadAnimation(context, R.anim.add_mask_out));
        hasOpen = false;
    }

    /**
     * 对话框是否已经打开
     *
     * @return
     */
    public boolean isShow() {
        return hasOpen;
    }

    /**
     * 获取弹出框的容器,用来自己添加View
     *
     * @return
     */
    public FrameLayout getPopupView() {
        return fl_pop;
    }

    /**
     * 获取内容的容器,用来自己添加View
     *
     * @return
     */
    public FrameLayout getContentView() {
        return fl_content;
    }

    /**
     * 获取tab的容器,用来自己添加View
     *
     * @return
     */
    public FrameLayout getTabView() {
        return ll_tab;
    }
}

动画文件:
add_mask_in.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
    android:duration="250">
    <alpha
        android:fromAlpha="0"
        android:toAlpha="1" />
</set>
add_mask_out.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
    android:duration="250">
    <alpha
        android:fromAlpha="1"
        android:toAlpha="0" />
</set>
add_menu_in.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
    android:duration="250">
    <translate
        android:fromYDelta="-100%p"
        android:toYDelta="0" />
</set>
add_menu_out.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
    android:duration="250">
    <translate
        android:fromYDelta="0"
        android:toYDelta="-100%p" />
</set>

上面的代码都是完整的,直接copy可以使用,其中布局文件中有两张图片需要自己去修改,这两个图标我就不上传了。


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值