Android实现仿QQ登录可编辑下拉菜单

在Android里,直接提供的Spinner控件虽然可以实现下拉菜单的效果,但其效果并不理想,很多时候我们需要类似手机QQ那样既可以在文本框中直接输入编辑文字,可以在下拉菜单中选中或者删除菜单选项,并且下拉菜单并不是以遮罩整个手机屏幕方式,而是以浮动在屏幕上的效果出现。下面呢,就来实现一下这些效果。

最后效果为:       

 

此次主要以EdiText、PopupWindow、ListView及Adapter来实现这种下拉效果。具体实现步骤就不一步步详细介绍了,直接贴完整代码吧,注释比较详细,相信都能看得懂。

 

 

//主界面Activity代码:

[html] view
plain
copy

  1. public class SelectActivity extends Activity implements Callback {  
  2.     //PopupWindow对象  
  3.     private PopupWindow selectPopupWindow= null;  
  4.     //自定义Adapter  
  5.     private OptionsAdapter optionsAdapter = null;  
  6.     //下拉框选项数据源  
  7.     private ArrayList<String> datas = new ArrayList<String>();;   
  8.     //下拉框依附组件  
  9.     private LinearLayout parent;  
  10.     //下拉框依附组件宽度,也将作为下拉框的宽度  
  11.     private int pwidth;   
  12.     //文本框  
  13.     private EditText et;  
  14.     //下拉箭头图片组件  
  15.     private ImageView image;  
  16.     //恢复数据源按钮  
  17.     private Button button;  
  18.     //展示所有下拉选项的ListView  
  19.     private ListView listView = null;   
  20.     //用来处理选中或者删除下拉项消息  
  21.     private Handler handler;  
  22.     //是否初始化完成标志    
  23.     private boolean flag = false;  
  24.       
  25.     @Override  
  26.     public void onCreate(Bundle savedInstanceState) {  
  27.         super.onCreate(savedInstanceState);  
  28.         setContentView(R.layout.select);  
  29.     }  
  30.   
  31.     /**  
  32.      * 没有在onCreate方法中调用initWedget(),而是在onWindowFocusChanged方法中调用,  
  33.      * 是因为initWedget()中需要获取PopupWindow浮动下拉框依附的组件宽度,在onCreate方法中是无法获取到该宽度的  
  34.      */  
  35.     @Override  
  36.     public void onWindowFocusChanged(boolean hasFocus) {  
  37.         super.onWindowFocusChanged(hasFocus);  
  38.         while(!flag){  
  39.             initWedget();  
  40.             flag = true;  
  41.         }  
  42.           
  43.     }  
  44.       
  45.     /**  
  46.      * 初始化界面控件  
  47.      */  
  48.     private void initWedget(){  
  49.         //初始化Handler,用来处理消息  
  50.         handler = new Handler(SelectActivity.this);  
  51.           
  52.         //初始化界面组件  
  53.         parent = (LinearLayout)findViewById(R.id.parent);  
  54.         et = (EditText)findViewById(R.id.edittext);  
  55.         image = (ImageView)findViewById(R.id.btn_select);  
  56.           
  57.           
  58.         //获取下拉框依附的组件宽度  
  59.         int width = parent.getWidth();  
  60.         pwidth = width;  
  61.           
  62.         //设置点击下拉箭头图片事件,点击弹出PopupWindow浮动下拉框  
  63.         image.setOnClickListener(new View.OnClickListener() {  
  64.             @Override  
  65.             public void onClick(View v) {  
  66.                 if(flag){  
  67.                     //显示PopupWindow窗口  
  68.                     popupWindwShowing();  
  69.                 }  
  70.             }  
  71.         });  
  72.           
  73.         //初始化PopupWindow  
  74.         initPopuWindow();  
  75.           
  76.         button = (Button)findViewById(R.id.refresh);  
  77.         //设置点击事件,恢复下拉框列表数据,没有什么作用,纯粹是为了方便多看几次效果而设置  
  78.         button.setOnClickListener(new View.OnClickListener() {  
  79.             @Override  
  80.             public void onClick(View v) {  
  81.                 initDatas();  
  82.                 optionsAdapter.notifyDataSetChanged();  
  83.             }  
  84.         });  
  85.     }  
  86.   
  87.     /**  
  88.      * 初始化填充Adapter所用List数据  
  89.      */  
  90.     private void initDatas(){  
  91.           
  92.          datas.clear();  
  93.            
  94.          datas.add("北京");  
  95.          datas.add("上海");  
  96.          datas.add("广州");  
  97.          datas.add("深圳");  
  98.          datas.add("重庆");  
  99.          datas.add("青岛");  
  100.          datas.add("石家庄");  
  101.     }  
  102.       
  103.      /**  
  104.      * 初始化PopupWindow  
  105.      */   
  106.     private void initPopuWindow(){   
  107.           
  108.         initDatas();  
  109.           
  110.         //PopupWindow浮动下拉框布局  
  111.         View loginwindow = (View)this.getLayoutInflater().inflate(R.layout.options, null);   
  112.         listView = (ListView) loginwindow.findViewById(R.id.list);   
  113.           
  114.         //设置自定义Adapter  
  115.         optionsAdapter = new OptionsAdapter(this, handler,datas);   
  116.         listView.setAdapter(optionsAdapter);   
  117.           
  118.         selectPopupWindow = new PopupWindow(loginwindow, pwidth,LayoutParams.WRAP_CONTENT, true);   
  119.           
  120.         selectPopupWindow.setOutsideTouchable(true);   
  121.           
  122.         //这一句是为了实现弹出PopupWindow后,当点击屏幕其他部分及Back键时PopupWindow会消失,  
  123.         //没有这一句则效果不能出来,但并不会影响背景  
  124.         //本人能力极其有限,不明白其原因,还望高手、知情者指点一下  
  125.         selectPopupWindow.setBackgroundDrawable(new BitmapDrawable());    
  126.     }   
  127.   
  128.       
  129.       
  130.     /**  
  131.      * 显示PopupWindow窗口  
  132.      *   
  133.      * @param popupwindow  
  134.      */   
  135.     public void popupWindwShowing() {   
  136.        //将selectPopupWindow作为parent的下拉框显示,并指定selectPopupWindow在Y方向上向上偏移3pix,  
  137.        //这是为了防止下拉框与文本框之间产生缝隙,影响界面美化  
  138.        //(是否会产生缝隙,及产生缝隙的大小,可能会根据机型、Android系统版本不同而异吧,不太清楚)  
  139.        selectPopupWindow.showAsDropDown(parent,0,-3);   
  140.     }   
  141.        
  142.     /**  
  143.      * PopupWindow消失  
  144.      */   
  145.     public void dismiss(){   
  146.         selectPopupWindow.dismiss();   
  147.     }  
  148.   
  149.     /**  
  150.      * 处理Hander消息  
  151.      */  
  152.     @Override  
  153.     public boolean handleMessage(Message message) {  
  154.         Bundle data = message.getData();  
  155.         switch(message.what){  
  156.             case 1:  
  157.                 //选中下拉项,下拉框消失  
  158.                 int selIndex = data.getInt("selIndex");  
  159.                 et.setText(datas.get(selIndex));  
  160.                 dismiss();  
  161.                 break;  
  162.             case 2:  
  163.                 //移除下拉项数据  
  164.                 int delIndex = data.getInt("delIndex");  
  165.                 datas.remove(delIndex);  
  166.                 //刷新下拉列表  
  167.                 optionsAdapter.notifyDataSetChanged();  
  168.                 break;  
  169.         }  
  170.         return false;  
  171.     }   
  172. }  

自定义适配器Adapter代码:

[java] view
plain
copy

  1. public class OptionsAdapter extends BaseAdapter {  
  2.   
  3.     private ArrayList<String> list = new ArrayList<String>();   
  4.     private Activity activity = null;   
  5.     private Handler handler;  
  6.       
  7.     /** 
  8.      * 自定义构造方法 
  9.      * @param activity 
  10.      * @param handler 
  11.      * @param list 
  12.      */  
  13.     public OptionsAdapter(Activity activity,Handler handler,ArrayList<String> list){  
  14.         this.activity = activity;  
  15.         this.handler = handler;  
  16.         this.list = list;  
  17.     }  
  18.       
  19.     @Override  
  20.     public int getCount() {  
  21.         return list.size();  
  22.     }  
  23.   
  24.     @Override  
  25.     public Object getItem(int position) {  
  26.         return list.get(position);  
  27.     }  
  28.   
  29.     @Override  
  30.     public long getItemId(int position) {  
  31.         return position;  
  32.     }  
  33.   
  34.     @Override  
  35.     public View getView(final int position, View convertView, ViewGroup parent) {  
  36.         ViewHolder holder = null;   
  37.         if (convertView == null) {   
  38.             holder = new ViewHolder();   
  39.             //下拉项布局  
  40.             convertView = LayoutInflater.from(activity).inflate(R.layout.option_item, null);   
  41.             holder.textView = (TextView) convertView.findViewById(R.id.item_text);   
  42.             holder.imageView = (ImageView) convertView.findViewById(R.id.delImage);   
  43.               
  44.             convertView.setTag(holder);   
  45.         } else {   
  46.             holder = (ViewHolder) convertView.getTag();   
  47.         }   
  48.           
  49.         holder.textView.setText(list.get(position));  
  50.           
  51.         //为下拉框选项文字部分设置事件,最终效果是点击将其文字填充到文本框  
  52.         holder.textView.setOnClickListener(new View.OnClickListener() {  
  53.             @Override  
  54.             public void onClick(View v) {  
  55.                 Message msg = new Message();  
  56.                 Bundle data = new Bundle();  
  57.                 //设置选中索引  
  58.                 data.putInt("selIndex", position);  
  59.                 msg.setData(data);  
  60.                 msg.what = 1;  
  61.                 //发出消息  
  62.                 handler.sendMessage(msg);  
  63.             }  
  64.         });  
  65.           
  66.         //为下拉框选项删除图标部分设置事件,最终效果是点击将该选项删除  
  67.         holder.imageView.setOnClickListener(new View.OnClickListener() {  
  68.             @Override  
  69.             public void onClick(View v) {  
  70.                 Message msg = new Message();  
  71.                 Bundle data = new Bundle();  
  72.                 //设置删除索引  
  73.                 data.putInt("delIndex", position);  
  74.                 msg.setData(data);  
  75.                 msg.what = 2;  
  76.                 //发出消息  
  77.                 handler.sendMessage(msg);  
  78.             }  
  79.         });  
  80.           
  81.         return convertView;   
  82.     }  
  83.   
  84. }  
  85.   
  86.   
  87. class ViewHolder {   
  88.     TextView textView;   
  89.     ImageView imageView;   
  90. }   

 

 

主界面布局select.xml文件:

[html] view
plain
copy

  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  3.     android:orientation="vertical"  
  4.     android:layout_width="fill_parent"  
  5.     android:layout_height="fill_parent"  
  6.     android:background="#EEEED1"  
  7.     >  
  8. <LinearLayout android:id="@+id/parent" android:layout_width="wrap_content"   

[html] view
plain
copy

  1. android:layout_height="wrap_content" android:orientation="horizontal"   

[html] view
plain
copy

  1.      android:layout_marginTop="50dp" android:layout_marginLeft="30dp">  
  2. <EditText android:id="@+id/edittext" android:layout_width="200dp"  android:singleLine="true"  
  3.     android:layout_height="40dp" android:background="@drawable/bg1" android:paddingLeft="3dp"/>  
  4. <ImageView android:id="@+id/btn_select" android:layout_width="30dp" android:layout_height="40dp"   
  5.     android:src="@drawable/img1" android:scaleType="fitXY"/>  
  6. </LinearLayout>  
  7. <Button android:id="@+id/refresh" android:layout_width="wrap_content" android:layout_height="45dp"  
  8.     android:text="恢复" android:textColor="#000000" android:textSize="20sp"   

[html] view
plain
copy

  1. android:layout_marginTop="30dp" android:layout_marginLeft="30dp"/>  
  2. lt;/LinearLayout>  

 

 

PopupWindow浮动下拉框布局options.xml文件:

[html] view
plain
copy

  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  3.     android:orientation="vertical"  
  4.     android:layout_width="fill_parent"  
  5.     android:layout_height="wrap_content"  
  6.     android:gravity="center_horizontal"  
  7.     >  
  8. <ListView android:id="@+id/list" android:layout_width="fill_parent"  
  9.     android:layout_height="wrap_content" android:cacheColorHint="#00000000">  
  10. </ListView>  
  11. </LinearLayout>  

 

下拉选项布局option_item.xml文件:

[html] view
plain
copy

  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  3.     android:layout_width="fill_parent"  
  4.     android:layout_height="fill_parent"  
  5.     android:background="#235654"  
  6.     >  
  7. <RelativeLayout  
  8.     android:layout_width="wrap_content"  
  9.     android:layout_height="wrap_content"  
  10.     android:gravity="center_vertical"  
  11.     android:minHeight="40dp"  
  12.     >  
  13. <ImageView android:id="@+id/delImage" android:layout_width="20dp"  

[html] view
plain
copy

  1.      android:layout_height="wrap_content" android:src="@drawable/del" android:textSize="18sp"  
  2.     android:layout_alignParentRight="true" android:layout_marginRight="10dp"/>  
  3. <TextView android:id="@+id/item_text"  android:layout_height="wrap_content"  
  4.      android:layout_width="fill_parent" android:layout_toLeftOf="@id/delImage"  
  5.       android:paddingLeft="5dp" android:layout_alignParentLeft="true"></TextView>  
  6. </RelativeLayout>  
  7. </LinearLayout>  
时间: 2024-09-27 12:03:40

Android实现仿QQ登录可编辑下拉菜单的相关文章

jquery仿QQ登录账号选择下拉框效果_jquery

QQ登录的时候,可以选择以前登录过的账户,这个东西也可以在网站登录的时候用到,所以我就想做一个这样的插件:在网上查了很多,没有找到合适自己的,所以决定自动制作一个. 原理就是一个textbox加一个ul模拟下拉框,用font模拟一个下拉按钮. 一.制作静态效果 先用css和html,做出一个应该有的样子.这里这两个我使用的是字体,可以在icomoon网站上面自己制作.用字体的好处是和输入框定位很方便,而且还可以控制大小颜色等,唯一的不足是IE6和IE7由于不支持:before选择器,导致无法显示

仿保时捷官网多级下拉菜单效果

妙味官网 妙味课堂--作品 妙味课堂--关于我们 妙味课堂--在线留言 妙味茶馆 妙味茶馆--视频教程 妙味茶馆--生活秀 妙味茶馆--特效兜 妙味茶馆--技术交流 妙味茶馆--聊吧 妙味--xhtml+css课程 零基础精品课程 页面架构师课程 妙味--javascript课程 网络教学课程 精通JavaScript开发课程 妙味课堂--作品 般固(Banggoo)网站,从网站策划.设计.制作.后台整个过程全执行,网站虽小,修改时间旷日持久,历时二个月完成.... 妙味课堂--关于我们 妙味课

关于下拉菜单的问题

问题描述 下拉菜单,如何做成可编辑的.不仅可以下拉选择,还可以手动输入 解决方案 解决方案二:搜索:编辑下拉框解决方案三:出来了.是把文本框和下拉菜单结合在一起使用的解决方案四:有谁做的在数字电视上操作的可编辑下拉菜单,我做的,在电脑上可以,可是在数字电视上用就不行了

Android 高仿QQ滑动弹出菜单标记已读、未读消息

  在上一篇博客<Android 高仿微信(QQ)滑动弹出编辑.删除菜单效果,增加下拉刷新功能>里,已经带着大家学习如何使用SwipeMenuListView这一开源库实现滑动列表弹出菜单,接下来,将进一步学习,如何为不同的list item呈现不同的菜单,此处我们做一个实例:Android 高仿QQ滑动弹出菜单标记已读.未读消息,看下效果图: 1. 创建项目,并导入SwipeMenuListView类库 2. 创建消息实体bean: public class Msg { public int

Android 高仿QQ图片选择器_Android

当做一款APP,需要选择本地图片时,首先考虑的无疑是系统相册,但是Android手机五花八门,再者手机像素的提升,大图无法返回等异常因数,导致适配机型比较困难,微信.QQ都相继的在自己的APP里集成了图片选择功能,放弃了系统提供的图片选择器,这里仿造QQ做了一个本地图片选择器,PS:之前有人说"仿"写成"防"了,今儿特意注意了下,求不错. 先上一张效果图,无图无真相啊~~~ 实现的效果大概是这样的: 1.单选:跳转到本地图片选择文件夹,选择文件夹后,进入到该文件夹下

Android开发仿QQ空间根据位置弹出PopupWindow显示更多操作效果_Android

我们打开QQ空间的时候有个箭头按钮点击之后弹出PopupWindow会根据位置的变化显示在箭头的上方还是下方,比普通的PopupWindow弹在屏幕中间显示好看的多. 先看QQ空间效果图: 这个要实现这个效果可以分几步进行 1.第一步自定义PopupWindow,实现如图的样式,这个继承PopupWindow自定义布局很容易实现 2.得到点击按钮的位置,根据位置是否在屏幕的中间的上方还是下方,将PopupWindow显示在控件的上方或者下方 3.适配问题,因为PopupWindow上面的操作列表

Android 高仿QQ 沉浸式状态栏_Android

前言: 在进入今天正题前,还是老样子先谈谈感想吧,最近感觉整个都失去了方向感,好迷茫!找工作又失败了,难道Android真的饱和了?这两天我一直没出门,除了下楼哪外卖就是宅宿舍了,静想了许久,我还是不能忘了初心,我相信我找不到工作的原因有很多,最关键的还是要技术够硬才行啊,奔跑吧孩子!接下来我就给大家介绍怎样快速打造沉浸式状态栏吧,虽然感觉有点相见恨晚,但其实不完! 一:何为沉浸式状态栏? 沉浸式状态栏是Google从Android 4.4开始,给我们开发者提供的一套能透明的系统ui样式,这样样

Android开发Popwindow仿微信右上角下拉菜单实例代码_Android

先给大家看下效果图: MenuPopwindow: package com.cloudeye.android.cloudeye.view; import android.app.Activity; import android.content.Context; import android.graphics.drawable.ColorDrawable; import android.view.LayoutInflater; import android.view.View; import an

Android 高仿QQ图片选择器

当做一款APP,需要选择本地图片时,首先考虑的无疑是系统相册,但是Android手机五花八门,再者手机像素的提升,大图无法返回等异常因数,导致适配机型比较困难,微信.QQ都相继的在自己的APP里集成了图片选择功能,放弃了系统提供的图片选择器,这里仿造QQ做了一个本地图片选择器,PS:之前有人说"仿"写成"防"了,今儿特意注意了下,求不错. 先上一张效果图,无图无真相啊~~~ 实现的效果大概是这样的: 1.单选:跳转到本地图片选择文件夹,选择文件夹后,进入到该文件夹下