LinearLayout详解四:彻底解决软键盘遮挡输入框的问题

之前把预备知识都介绍完了,话说学以致用,接下来我们要通过重载LinearLayout类来解决软键盘覆盖的问题。

首先阐述一下这个问题,如下图所示:

然后看挡住输入框的情况

然后我们给出xml的源代码:

<LinearLayout 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"
    android:orientation="vertical"
    android:paddingBottom="@dimen/activity_vertical_margin"
    android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    tools:context=".MainActivity" >

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="6"
        android:background="#ff0000"
        android:orientation="vertical" >

        <TextView
            android:id="@+id/textView1"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="@string/login_title" />
    </LinearLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_marginTop="20dp"
        android:layout_weight="3"
        android:orientation="vertical" >
    <EditText
        android:id="@+id/editText1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignLeft="@+id/textView1"
        android:layout_alignParentBottom="true"
        android:layout_gravity="center_vertical"
        android:hint="用户名"
        android:ems="10" >

        <requestFocus />
    </EditText>

    <EditText
        android:id="@+id/editText1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignLeft="@+id/textView1"
        android:layout_alignParentBottom="true"
        android:layout_gravity="center_vertical"
        android:hint="用户名"
        android:ems="10" >

        <requestFocus />
    </EditText>
    </LinearLayout>

</LinearLayout>

虽然我知道,看代码是多么让人蛋。疼的事情,但请大家还是忍住对我的菊,花猛踹一脚的愤怒看一下我辛辛苦苦垒的代码吧。

这个层次其实一点都不复杂就是外面一层linearlayout,他内部包含两个linearlayout,这是再正常不过的登录界面了:上面是logo,下面是用户名,密码输入框。困扰大家的问题就是弹出来的软键盘会遮挡输入框。这个比iOS的烦人多了,iOS解决这类问题还是比较简单的,直接代码搞定就可以了。

现在讲一下通常的解决方案就是:监听键盘弹出,然后隐藏上面的logo,然后自然而然的下面的也就顶上去了。怎么实现呢,我们只要写一个类继承自LinearLayout即可。

我们写一个类:LinearLayoutView.java 源代码如下:

package com.example.overidelinearlayout;

import android.content.Context;
import android.os.Handler;
import android.util.AttributeSet;
import android.util.Log;
import android.widget.LinearLayout;

public class LinearLayoutView extends LinearLayout{

	public static final int KEYBORAD_HIDE = 0;
	public static final int KEYBORAD_SHOW = 1;
	private static final int SOFTKEYPAD_MIN_HEIGHT = 50;

	private Handler uiHandler = new Handler();

	public LinearLayoutView(Context context) {
		super(context);
		// TODO Auto-generated constructor stub
	}

	public LinearLayoutView(Context context, AttributeSet attrs) {
		super(context, attrs);

		// TODO Auto-generated constructor stub
	}

	@Override
	protected void onSizeChanged(int w,final int h, int oldw,final int oldh) {
		// TODO Auto-generated method stub
		super.onSizeChanged(w, h, oldw, oldh);
		uiHandler.post(new Runnable() {
			@Override
			public void run() {
				if (oldh - h > SOFTKEYPAD_MIN_HEIGHT){
					Log.e("lp", "up");
					System.out.println("弹起");
					keyBordStateListener.stateChange(KEYBORAD_SHOW);
				}
				else {
					System.out.println("隐藏");
					Log.e("lp", "down");
					if(keyBordStateListener != null){
						keyBordStateListener.stateChange(KEYBORAD_HIDE);
					}
				}
			}
		});
	}

	@Override
	protected void onLayout(boolean changed, int l, int t, int r, int b) {
		// TODO Auto-generated method stub
		super.onLayout(changed, l, t, r, b);
	}

	@Override
	protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
		// TODO Auto-generated method stub
		super.onMeasure(widthMeasureSpec, heightMeasureSpec);
	}

	private KeyBordStateListener  keyBordStateListener;

	public void setKeyBordStateListener(KeyBordStateListener keyBordStateListener) {
		this.keyBordStateListener = keyBordStateListener;
	}

	public interface KeyBordStateListener{
		public void stateChange(int state);
	}

}

然后我们把xml最上层的linearlayout改为LinearLayoutView即可,然后给他们加上id,更新后的xml如下:

<com.example.overidelinearlayout.LinearLayoutView xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:id="@+id/login_root_layout"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:paddingBottom="@dimen/activity_vertical_margin"
    android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    tools:context=".MainActivity" >

    <LinearLayout
        android:id="@+id/login_layout_logo"
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="6"
        android:background="#ff0000"
        android:orientation="vertical" >

        <TextView
            android:id="@+id/textView1"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="@string/login_title" />
    </LinearLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_marginTop="20dp"
        android:layout_weight="3"
        android:orientation="vertical" >
    <EditText
        android:id="@+id/editText1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignLeft="@+id/textView1"
        android:layout_alignParentBottom="true"
        android:layout_gravity="center_vertical"
        android:hint="用户名"
        android:ems="10" >

        <requestFocus />
    </EditText>

    <EditText
        android:id="@+id/editText1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignLeft="@+id/textView1"
        android:layout_alignParentBottom="true"
        android:layout_gravity="center_vertical"
        android:hint="用户名"
        android:ems="10" >

        <requestFocus />
    </EditText>
    </LinearLayout>

</com.example.overidelinearlayout.LinearLayoutView>

然后我们再写MainActivity里面的代码:

package com.example.overidelinearlayout;

import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.LinearLayout;

import com.example.overidelinearlayout.LinearLayoutView.KeyBordStateListener;

public class MainActivity extends Activity implements KeyBordStateListener {

	private LinearLayoutView resizeLayout;
	private LinearLayout logoLayout;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);

		resizeLayout = (LinearLayoutView) findViewById(R.id.login_root_layout);
		logoLayout = (LinearLayout) findViewById(R.id.login_layout_logo);
		resizeLayout.setKeyBordStateListener(this);
	}

	@Override
	public void stateChange(int state) {
		// TODO Auto-generated method stub
		switch (state) {
		case LinearLayoutView.KEYBORAD_HIDE:
			logoLayout.setVisibility(View.VISIBLE);
			break;
		case LinearLayoutView.KEYBORAD_SHOW:
			logoLayout.setVisibility(View.GONE);
			break;
		}
	}

}

最后别忘了在manifest中这样写:

<activity
            android:name="com.example.overidelinearlayout.MainActivity"
            android:windowSoftInputMode="adjustResize"  >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>

最后看一下效果吧:

搞定收工!

最后附上源代码:源代码在此,请猛戳!(虽然本来不想给的,省得大家都不懂脑筋,但回头想想又不忍心,毕竟本人也经历过到处看教程却苦于没代码的岁月。被项目压着的日子不好过啊!!!看着嗷嗷待哺的诸位着实有点于心不忍)

LinearLayout详解四:彻底解决软键盘遮挡输入框的问题

时间: 2024-10-12 14:31:38

LinearLayout详解四:彻底解决软键盘遮挡输入框的问题的相关文章

安卓H5软键盘遮挡输入框

<div class="label"> * <span><?php echo lang('receive_email_info'); ?></span> <input class="r-email" type="text" placeholder="<?php echo lang('please_in_receive_email'); ?>3333"> &

【幻化万千戏红尘】qianfeng-Android-Day01-历史、环境搭建、VIEW属性、LinearLayout详解基础学习

一.模拟器:1.夜神2.Genymotion 二.Android环境变量配置:Android_SDK_HOME:D:\Program\android\SDKForEclipsePath:%Android_SDK_HOME%\tools;%Android_SDK_HOME%\platform-tools 三.adb命令:查看所有模拟器:android list avd启动模拟器:emulator -avd 模拟器名称安装App:adb install 应用名.apk卸载App:adb uninst

LinearLayout详解二:从其父类View说起

这个View类说来就话长了,但我们又不得不说,要说呢,就得说的彻底,要让大家看得一清二楚,明明白白.所以我们就从源代码角度来看一个view是如何被加载的吧. 如果大家不知道怎么下载android的源代码,或者说懒得去下载(因为源代码确实比较大,大概有10G)的话,教大家几个取巧的办法: 1.直接在google中输入"android view.java"即可.这种方法成功率非常高,一般android的比较重要的类都能搜到. 2.给大家提供一个人家用于放源码的的git:[email pro

LinearLayout详解三:LayoutInflater创建View过程分析

项目人力资源管理主要有以下几个过程: 编制人力资源管理计划 组建项目团队 建设项目团队 项目团队管理 编制人力资源管理计划 根据什么来编? 直观点就是你要干什么事?干这些事有哪些制约? 这个说起来好像和没说一样,但就我自己做的一些项目来说,有以下困难: 1> 项目前期需求是不具体不明确的 这样直接导致你做项目计划时WBS也是不明确的,进而你细化不了活动,自然你也没法 明确活动需要什么样的人. 这个时候怎么办? 就我个人而言,有2种员工很喜欢: 1> 数学思维强的, 注意不是会做高数题,是指给你

解决 Android 软键盘挡住输入框的问题

当在Android的layout设计里面如果输入框过多,则在输入弹出软键盘的时候,下面的输入框会有一部分被软件盘挡住,从而不能获取焦点输入. 下面提供三种解决办法:    方法一:在你的activity中的对应的java文件中oncreate中setContentView之前写上这个代码getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN); 该方法是最简单的    方法二:在 项目的Andro

如何解决软键盘弹出引起的各种不适

1.如何解决软键盘弹出引起的各种不适 2.android软键盘弹出引起的各种不适终极解决方案 3.android软键盘弹出引起的各种不适终极解决方案 4.android软键盘弹出,会把原来的界面挤上去的问题 处理方法 5.Android 关于弹出键盘问题的几种情况和解决方案 6.Android 弹出软键盘问题(最终解决方法) 7.Android 软键盘显示隐藏监听解决方案

Android基础入门教程——8.3.7 Paint API之—— Xfermode与PorterDuff详解(四)

Android基础入门教程--8.3.7 Paint API之-- Xfermode与PorterDuff详解(四) 标签(空格分隔): Android基础入门教程 本节引言: 上节我们写了关于Xfermode与PorterDuff使用的第一个例子:圆角&圆形图片ImageView的实现, 我们体会到了PorterDuff.Mode.DST_IN给我们带来的好处,本节我们继续来写例子练练手, 还记得Android基础入门教程--8.3.2 绘图类实战示例给大家带来的拔掉美女衣服的实现吗? 当时我

Android软键盘遮挡的四种解决方案

问题概述 在编辑框输入内容时会弹出软键盘,而手机屏幕区域有限往往会遮住输入界面,我们先看一下问题效果图: 输入用户名和密码时,系统会弹出键盘,造成系统键盘会挡住文本框的问题,如图所示: 输入密码时输入框被系统键盘遮挡了,大大降低了用户操作体验,这就是开发中非常常见的软键盘遮挡的问题,该如何解决? 简单解决方案  方法一 在你的activity中的oncreate中setContentView之前写上这个代码 getWindow().setSoftInputMode(WindowManager.L

LinearLayout详解一:LinearLayout本质

LinearLayout,中文意思是线性布局.如果你是初学android的,肯定会很困惑"啥叫布局",啥又叫"线性布局"呢. 有的时候,我尝试用官方的语言去解释,但结果总是让人很懊恼.所以我只能跟大家通俗的说"LinearLayout"就是一个View,即视图,它跟Button按钮,Label标签一样,有自己的属性,比如说,高度,宽度,背景色等等.那么跟Button按钮,Label标签有啥区别呢.其实也很简单,就是这个LinearLayout他比