Android 一个美观简洁的登录界面(一)

       Android 一个美观简洁的登录界面

输入框样式

 一.登录式样1:

1.效果图:

2.布局代码:

<?xml version="1.0" encoding="utf-8"?>
<!--登录界面,用LinearLayout-->
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="@drawable/wallpaper_11"
    android:orientation="vertical">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_marginTop="35dp">

        <ImageView
            android:id="@+id/symbol"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            />

        <TextView
            android:layout_marginLeft="20dp"
            android:id="@+id/qq"
            android:layout_width="wrap_content"
            android:layout_marginTop="35dp"
            android:text="仿QQ"
            android:textColor="@color/white"
            android:textSize="24sp"
            android:layout_height="wrap_content" />
    </LinearLayout>
    <!--输入框-->
    <EditText
        android:id="@+id/et_user_name"
        android:layout_width="320dp"
        android:layout_height="wrap_content"
        android:layout_gravity="center"
        android:paddingLeft="10dp"
        android:theme="@style/MyEditText"
        android:drawablePadding="@dimen/dp_10"
        android:drawableLeft="@mipmap/msg_icon"
        android:textColor="@color/white"
        android:textColorHint="@color/white"
        android:layout_marginTop="60dp"
        android:hint="账号"
        android:textSize="20sp" />
    <!--输入框-->
    <EditText
        android:id="@+id/et_psw"
        android:layout_width="320dp"
        android:layout_height="wrap_content"
        android:layout_gravity="center"
        android:layout_marginTop="10dp"
        android:hint="密码"
        android:drawablePadding="@dimen/dp_10"
        android:drawableLeft="@mipmap/msg_icon"
        android:textColor="@color/white"
        android:paddingLeft="10dp"
        android:theme="@style/MyEditText"
        android:textColorHint="@color/white"
        android:textSize="20sp"
        android:inputType="textPassword"/>
    <!--按钮-->
    <Button
        android:id="@+id/btn_login"
        android:text="登录"
        android:background="#1E90FF"
        android:textSize="24sp"
        android:textColor="@color/white"
        android:layout_gravity="center"
        android:layout_marginTop="20dp"
        android:layout_width="320dp"
        android:layout_height="wrap_content"/>

    <RelativeLayout
        android:layout_marginTop="15dp"
        android:layout_width="match_parent"
        android:layout_height="wrap_content">
        <TextView
            android:id="@+id/tv_register"
            android:layout_alignParentRight="true"
            android:layout_marginRight="20dp"
            android:textColor="@color/white"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="新用户注册"/>
        <!--layout_weight="1" layout_width="0dp"实现均分效果-->
        <TextView
            android:id="@+id/tv_find_psw"
            android:layout_alignParentLeft="true"
            android:layout_marginLeft="20dp"
            android:textColor="@color/white"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="忘记密码?" />
    </RelativeLayout>
    <LinearLayout
        android:orientation="vertical"
        android:layout_width="match_parent"
        android:layout_height="wrap_content">
        <RelativeLayout
            android:layout_gravity="center"
            android:layout_marginBottom="30dp"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content">

            <TextView
                android:textColor="@color/white"
                android:layout_alignParentBottom="true"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="登录即代表阅读并同意服务条款" />
        </RelativeLayout>
    </LinearLayout>
</LinearLayout>

3.设置AppCompatEditText(EditText)的下划线和光标显示的颜色,自定义默认和选中的颜色设置:

在style中配置

 <style name="MyEditText" parent="Theme.AppCompat.Light">
        <item name="colorControlNormal">@color/white</item>
        <item name="colorControlActivated">@color/colorConfirm</item>
    </style>

4.android:textCursorDrawable 自定义光标样式,设置为”@null”之后发现光标的样式会变得跟文字的颜色一样

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
 android:shape="rectangle">
 <size android:width="2dp" />
 <solid android:color="@android:color/holo_blue_light" />
</shape>
<EditText
android:textCursorDrawable="@drawable/cursor_color"
android:hint="自定义光标颜色"
android:layout_width="match_parent"
android:layout_height="wrap_content" />

5.5.0一下的手机显示下划线可以会有问题,Material Design风格体现不出来,可以这样处理:

设置选择状态:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
 <item android:state_focused="false" android:drawable="@drawable/et_underline_unselected"/>
 <item android:state_focused="true" android:drawable="@drawable/et_underline_selected"/>
</selector>

 et_underline_unselected.xml

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
 <item
  android:bottom="0dp"
  android:left="-2dp"
  android:right="-2dp"
  android:top="-2dp">
  <shape>
   <solid android:color="@android:color/transparent" />
   <stroke
    android:width="1dp"
    android:color="@android:color/darker_gray" />
   <padding android:bottom="4dp" />
  </shape>
 </item>
 
</layer-list>

et_underline_selected.xml

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
 
 <item
  android:bottom="0dp"
  android:left="-2dp"
  android:right="-2dp"
  android:top="-2dp">
  <shape>
   <solid android:color="@android:color/transparent" />
   <stroke
    android:color="@android:color/holo_green_light"
    android:width="2dp" />
   <padding android:bottom="4dp" />
 
  </shape>
 </item>
 
</layer-list>
/**初始化EditText,默认都为未选中状态**/
editText1.setBackgroundResource(R.drawable.et_underline_unselected);
editText2.setBackgroundResource(R.drawable.et_underline_unselected);
/**第一个EditText的焦点监听事件**/
editText1.setOnFocusChangeListener(new View.OnFocusChangeListener() {
 @Override
 public void onFocusChange(View v, boolean hasFocus) {
  if (hasFocus) {
   Log.e(TAG, "EditText1获得焦点");
   editText1.setBackgroundResource(R.drawable.et_underline_selected);
 
  } else {
   Log.e(TAG, "EditText1失去焦点");
   editText1.setBackgroundResource(R.drawable.et_underline_unselected);
  }
 }
});
/**第二个EditText的焦点监听事件**/
editText2.setOnFocusChangeListener(new View.OnFocusChangeListener() {
 @Override
 public void onFocusChange(View v, boolean hasFocus) {
  if (hasFocus) {
   Log.e(TAG, "EditText2获得焦点");
   editText2.setBackgroundResource(R.drawable.et_underline_selected);
 
  } else {
   Log.e(TAG, "EditText2失去焦点");
   editText2.setBackgroundResource(R.drawable.et_underline_unselected);
  }
 }
});

二.登录式样2:

1.效果图:

2.布局代码:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".ui.activity.sgf.login.MyLoginActivity">
    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical"
        android:background="@drawable/wallpaper_11"
        android:gravity="center">
        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:paddingBottom="30dp"
            android:paddingTop="20dp"
            android:background="#99404348"
            android:gravity="center">
            <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_gravity="center"
                android:text="Welcome"
                android:textColor="#FFFFFF"
                android:textSize="18sp"/>
        </LinearLayout>
        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="vertical"
            android:paddingBottom="20dp"
            android:paddingTop="20dp"
            android:background="#99000000">
            <EditText
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:background="@null"
                android:layout_gravity="center"
                android:layout_marginRight="50dp"
                android:layout_marginLeft="50dp"
                android:textColor="#9F9FA0"
                android:textColorHint="#9F9FA0"
                android:hint="your username"/>

            <View
                android:layout_width="match_parent"
                android:layout_height="1dip"
                android:background="#83738F"
                android:layout_marginRight="40dp"
                android:layout_marginLeft="40dp"
                android:layout_marginTop="10dp"
                android:layout_marginBottom="5dp"></View>

            <EditText
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:background="@null"
                android:layout_gravity="center"
                android:hint="your password"
                android:textColor="#9F9FA0"
                android:textColorHint="#9F9FA0"
                android:layout_marginLeft="50dp"
                android:layout_marginRight="50dp"/>
        </LinearLayout>
        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:paddingBottom="30dp"
            android:paddingTop="20dp"
            android:background="#99404348"
            android:gravity="center"
            android:orientation="horizontal">
            <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_gravity="center"
                android:text="Forget Password?"
                android:textColor="#DDDDDD"
                android:textSize="15sp"/>
            <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_gravity="center"
                android:text="Tap Here"
                android:textColor="#FFFFFF"
                android:textSize="15sp"/>
        </LinearLayout>

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="horizontal">
            <Button
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginLeft="40dp"
                android:layout_marginRight="10dp"
                android:layout_weight="1"
                android:background="@drawable/buttonstyle"
                android:text="Login"/>
            <Button
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginRight="40dp"
                android:layout_marginLeft="10dp"
                android:background="@drawable/buttonstyle"
                android:layout_weight="1"
                android:text="Sign in"/>
        </LinearLayout>

    </LinearLayout>

</LinearLayout>

圆角背景 

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_pressed="false">
        <shape>
            <!-- 色值 -->
            <solid android:color="#585EE0" />
            <!-- 圆角 -->
            <corners android:radius="10dp" />
        </shape>
    </item>
    <item android:state_pressed="true">
        <shape>
            <!-- 色值 -->
            <solid android:color="#289BE5" />
            <!-- 圆角 -->
            <corners android:radius="10dp" />
        </shape>
    </item>
</selector>

要是你想使用圆角背景渐变色的话可以看看下面:

<?xml version="1.0" encoding="utf-8"?> 
<shape xmlns:android="http://schemas.android.com/apk/res/android"> 
    <gradient  
        android:startColor="#3A3C39"  
        android:endColor="#181818" 
        android:angle="270" 
     /> 
    <corners android:radius="0dp" /> 
</shape>

 其中 android:angle="270"  代表方向, 270表示从上到下,180表示从右到左,默认从左

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
    <gradient
        android:angle="90"
        android:endColor="@color/colorPrimary"
        android:startColor="@color/colorAccent" />
</shape>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="rectangle">
    <gradient android:type="radial" android:gradientRadius="250"
        android:startColor="#E9E9E9" android:endColor="#D4D4D4" />
</shape>
 
 
<shape xmlns:android="http://schemas.android.com/apk/res/android">
 <gradient android:angle="0" android:startColor="#FFdaf3fc"
  android:centerColor="#FFd4e9a9" android:endColor="#FFdaf3fc"/>
</shape>

 在这里要注意android:type="radial"类型的使用会有不同的效果,android:centerColor="#FFd4e9a9" 通常这个也不是被人常用

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
	<gradient 
		android:startColor="#FFACDAE5"
		android:endColor="#FF72CAE1"
		android:angle="45"
	/>
</shape>
Android背景色渐变(左上->右下)
<gradient
    android:angle="135"
    android:centerColor="#4CAF50"
    android:endColor="#2E7D32"
    android:startColor="#81C784"
    android:type="linear" />

在这里设置背景上下渐变色 设置背景左右渐变色都是可以的

 
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
	android:shape="rectangle">
	<gradient android:startColor="#509245" android:centerColor="#3e8532"
		android:endColor="#509245" android:type="linear" android:angle="90"
		android:centerX="0.5" android:centerY="0.5" />
	<padding android:left="7dp" android:top="7dp" android:right="7dp"
		android:bottom="7dp" />
	<corners android:radius="4dp" />
</shape>

android:shape 配置的是图形的形式,主要包括方形、圆形等,上边代码为方形。gradient节点主要配置起点颜色、终点颜色、中间点的坐标、中间点的颜色、渐变角度(90度为上下渐变,0为左右渐变),padding节点主要配置上下左右边距,corners节点配置四周园角的半径。 

三.登录式样三(EditText、TextInputLayout、AppCompatEditText、ClearEditText等)

1.布局:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">
    <!--android.support.design:hintAnimationEnabled | 是否显示hint的动画,默认true-->
    <!--android.support.design:hintEnabled | 是否使用hint属性,默认true-->
    <!--android.support.design:hintTextAppearance | 设置hint的文字样式(指运行动画效果之后的样式)-->
    <!--android.support.design:counterEnabled | 是否显示计数器-->
    <!--android.support.design:counterMaxLength | 设置计数器的最大值-->
    <!--android.support.design:counterOverflowTextAppearance | 输入字符大于我们限定个数字符时的样式-->
    <!--app:theme 设置浮动标签的颜色主题-->
    <!--EditText 设置左侧图片,系统建议drawableStart/drawableLeft一起用,API>17-->
    <!--android.support.design:passwordToggleEnabled | 是否显示密码开关图片,需要EditText设置inputType-->
    <!--android.support.design:passwordToggleTint | 设置密码开关图片颜色-->
    <!--android.support.design:passwordToggleTintMode | 设置密码开关图片(混合颜色模式),与passwordToggleTint同时使用-->
    <!--android.support.design:errorEnabled |是否显示错误信息-->
    <!--android.support.design:errorTextAppearance| 错误信息的字体样式-->

    <!--系统默认的密码开关(修改颜色主题)-->
    <ScrollView
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:orientation="vertical">

            <com.google.android.material.textfield.TextInputLayout
                android:id="@+id/textinputlayout_name"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginTop="60dp"
                android:theme="@style/CustomAppTheme_textinputLayout">

                <EditText
                    android:id="@+id/et_name"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:hint="请输入用户名" />
            </com.google.android.material.textfield.TextInputLayout>

            <com.google.android.material.textfield.TextInputLayout
                android:id="@+id/textinputlayout_email"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginTop="20dp"
                android:theme="@style/CustomAppTheme_textinputLayout"
                app:errorEnabled="true">

                <com.hjq.widget.view.ClearEditText
                    android:id="@+id/et_email"
                    style="@style/MyEditText"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:hint="请输入邮箱" />
            </com.google.android.material.textfield.TextInputLayout>
            <!--app:counterTextAppearance="@style/Mystyle"-->
            <!--app:counterOverflowTextAppearance="@style/HintError"-->
            <com.google.android.material.textfield.TextInputLayout
                android:id="@+id/textinputlayout_password"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginTop="20dp"
                android:theme="@style/CustomAppTheme_textinputLayout"
                app:counterEnabled="true"
                app:counterMaxLength="5"
                app:counterOverflowTextAppearance="@style/HintError"
                app:counterTextAppearance="@style/Mystyle"
                app:hintTextAppearance="@style/Mystyle"
                app:passwordToggleEnabled="true"
                app:passwordToggleTint="@color/white">

                <EditText
                    android:id="@+id/et_password"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:hint="请输入密码"
                    android:inputType="textPassword"
                    android:textColor="@color/white"
                    android:textColorHint="@color/white" />
            </com.google.android.material.textfield.TextInputLayout>

            <com.google.android.material.textfield.TextInputLayout
                android:id="@+id/textinputlayout_code"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginTop="20dp"
                android:theme="@style/CustomAppTheme_textinputLayout"
                app:counterEnabled="true"
                app:counterMaxLength="6"
                app:counterOverflowTextAppearance="@style/HintError"
                app:counterTextAppearance="@style/Mystyle"
                app:errorEnabled="true"
                app:errorTextAppearance="@color/white"
                app:hintTextAppearance="@style/Mystyle"
                app:passwordToggleEnabled="true"
                app:passwordToggleTint="@color/white">


                <EditText
                    android:id="@+id/et_code"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:hint="请输入验证码"
                    android:inputType="number"
                    android:textColor="@color/white"
                    android:textColorHint="@color/white" />
            </com.google.android.material.textfield.TextInputLayout>

            <!--验证码-->
            <RelativeLayout
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginTop="20dp"
                android:orientation="horizontal">
                <!--android:background="@drawable/bg_edittext_selector"-->
                <EditText
                    android:id="@+id/et_code2"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:layout_marginLeft="20dp"
                    android:layout_marginRight="20dp"
                    android:hint="请输入验证码"
                    android:inputType="number"
                    android:padding="10dp"
                    android:textColor="@color/white"
                    android:textColorHint="@color/white"
                    android:theme="@style/MyEditText" />

                <RelativeLayout
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"></RelativeLayout>

                <TextView
                    android:id="@+id/tv_code"
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:layout_alignParentRight="true"
                    android:layout_centerVertical="true"
                    android:layout_gravity="center|right"
                    android:layout_marginRight="20dp"
                    android:text="(60s)"
                    android:textColor="@color/white" />
            </RelativeLayout>

            <!--验证码-->
            <RelativeLayout
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginTop="20dp"
                android:orientation="horizontal">
                <!--android:background="@drawable/bg_edittext_selector"-->
                <EditText
                    android:id="@+id/et_code3"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:layout_marginLeft="20dp"
                    android:layout_marginRight="20dp"
                    android:hint="请输入验证码"
                    android:inputType="number"
                    android:padding="10dp"
                    android:textColor="@color/white"
                    android:textColorHint="@color/white"
                    android:theme="@style/MyEditText" />

                <RelativeLayout
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"></RelativeLayout>

                <TextView
                    android:id="@+id/tv_code3"
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:layout_alignParentRight="true"
                    android:layout_centerVertical="true"
                    android:layout_gravity="center|right"
                    android:layout_marginRight="20dp"
                    android:text="X"
                    android:textColor="@color/white" />
            </RelativeLayout>
            <EditText
                android:id="@+id/EditText2"
                android:layout_width="fill_parent"
                android:layout_height="36dip"
                android:layout_below="@+id/EditText"
                android:layout_margin="5dip"
                android:background="@drawable/line3"
                android:hint="请输入用户名"
                android:padding="5dip"
                android:singleLine="true"
                android:textColorHint="#AAAAAA"
                android:textSize="15dip" />
            <EditText
                android:id="@+id/EditText3"
                android:layout_width="fill_parent"
                android:layout_height="36dip"
                android:layout_below="@+id/EditText2"
                android:layout_margin="5dip"
                android:background="@drawable/line3"
                android:hint="自定义光标颜色"
                android:digits="1234567890qwertyuiopasdfghjklzxcvbnm"
                android:padding="5dip"
                android:textCursorDrawable="@drawable/bg_edittext"
                android:layerType="software"
                android:singleLine="true"
                android:textColorHint="#AAAAAA"
                android:textSize="15dip" />

            <Button
                android:id="@+id/bt_yes"
                android:text="确认"
                android:textColor="@color/white"
                android:textSize="18sp"
                android:layout_gravity="center"
                android:paddingLeft="120dp"
                android:paddingRight="120dp"
                android:background="@drawable/bt_blue"
                android:layout_width="wrap_content"
                android:layout_height="40dp" />
        </LinearLayout>
    </ScrollView>

</LinearLayout>

2.属性:

<style name="MyEditText" parent="Theme.AppCompat.Light">
        <item name="colorControlNormal">@color/white</item>
        <item name="colorControlActivated">@color/colorConfirm</item>
    </style>

    <style name="CustomAppTheme_textinputLayout" parent="Theme.AppCompat.Light.NoActionBar">

        <!-- <item name="colorAccent">#3498db</item> -->
        <item name="android:textColorHint">@color/gray</item>
        <item name="colorControlNormal">@color/gray</item>
        <item name="colorControlActivated">@color/colorAccent</item>
        <item name="colorControlHighlight">@color/colorAccent</item>
        <item name="android:windowTranslucentStatus">true</item>
    </style>

    <!--输入框设置颜色-->
    <style name="HintError" parent="TextAppearance.AppCompat">
        <item name="android:textColor">@color/red</item>
    </style>

    <style name="Mystyle" >
        <item name="android:textColor">#00aaff</item>
        <item name="android:textSize">16sp</item>
    </style>

bg_edittext.xml 

<?xml version="1.0" encoding="utf-8"?>
<shape
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="rectangle">
    <!--宽度-->
    <size android:width="1dp" />
    <!--色值-->
    <solid android:color="#3399dd"/>
</shape>

 bt_blue.xml

<?xml version="1.0" encoding="UTF-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
    <solid android:color="#0047CC" />
    <corners android:radius="8dip"/>
    <stroke
        android:width="1dip"
        android:color="#0047CC" />
</shape>  

3.主函数代码:

import android.os.Bundle;
import android.support.design.widget.TextInputLayout;
import android.support.v7.app.AppCompatActivity;
import android.text.Editable;
import android.text.TextUtils;
import android.text.TextWatcher;
import android.view.View;
import android.widget.EditText;

import com.example.m1571.mycolorfulnews.R;

import butterknife.ButterKnife;

/**
 * 登录输入框
 */
public class TextInputLayoutActivity extends AppCompatActivity {

    private TextInputLayout textinputlayout_email;
    private TextInputLayout textinputlayout_name;
    private TextInputLayout textinputlayout_password;
    private TextInputLayout textinputlayout_code;
    private EditText et_email;
    private EditText et_name;
    private EditText et_password;
    private EditText et_code;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_textinputlayout);
        ButterKnife.bind(this);

        et_name = findViewById(R.id.et_name);
        et_email = findViewById(R.id.et_email);
        et_password = findViewById(R.id.et_password);
        et_code = findViewById(R.id.et_code);
        textinputlayout_name = findViewById(R.id.textinputlayout_name);
        textinputlayout_email = findViewById(R.id.textinputlayout_email);
        textinputlayout_password = findViewById(R.id.textinputlayout_password);
        textinputlayout_code = findViewById(R.id.textinputlayout_code);
        et_email.addTextChangedListener(new TextWatcher() {
            @Override
            public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) {

            }

            @Override
            public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) {
//                if (!RegexUtils.isEmail(charSequence)) {
//                    textInputLayout.setError("邮箱格式错误");
//                    textInputLayout.setErrorEnabled(true);
//                } else {
//                    textInputLayout.setErrorEnabled(false);
//                }
                if (!isValidEmail(et_email.getText())) {
//                        edittext2.setError("Email is invalid");
//                        textInputLayout2.setError("Email is invalid");
                    textinputlayout_email.setError("邮箱格式错误");
                    textinputlayout_email.setErrorEnabled(true);
                } else {
//                        textinputlayout_email.setError(null);
                    textinputlayout_email.setErrorEnabled(false);
                }
                //邮箱输入框清空后,颜色恢复默认
                if (TextUtils.isEmpty(et_email.getText().toString().trim())) {
                    textinputlayout_email.setErrorEnabled(false);
                }
                if (charSequence.toString().length() < 1) {
                    textinputlayout_email.setErrorEnabled(false);
                }
            }

            @Override
            public void afterTextChanged(Editable editable) {

            }
        });
        et_email.setOnFocusChangeListener(new View.OnFocusChangeListener() {
            @Override
            public void onFocusChange(View v, boolean hasFocus) {

                if (!hasFocus) {
                    if (!isValidEmail(et_email.getText())) {
//                        et_email.setError("Email is invalid");
//                        textInputLayout2.setError("Email is invalid");
                    } else {
//                        textInputLayout2.setError(null);
                    }
                }
            }
        });
        et_code.addTextChangedListener(new TextWatcher() {
            @Override
            public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) {

            }

            @Override
            public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) {
//                if (!RegexUtils.isEmail(charSequence)) {
//                    textInputLayout.setError("邮箱格式错误");
//                    textInputLayout.setErrorEnabled(true);
//                } else {
//                    textInputLayout.setErrorEnabled(false);
//                }
                if (!isValidEmail(et_code.getText())) {
//                        edittext2.setError("Email is invalid");
                    et_code.setError("Email is invalid");
                    textinputlayout_code.setError("邮箱格式错误");
                    textinputlayout_code.setErrorEnabled(true);
                } else {
                    textinputlayout_code.setError(null);
                    textinputlayout_code.setErrorEnabled(false);
                }
                //邮箱输入框清空后,颜色恢复默认
                if (TextUtils.isEmpty(et_code.getText().toString().trim())) {
                    textinputlayout_code.setErrorEnabled(false);
                }
                if (charSequence.toString().length() < 1) {
                    textinputlayout_code.setErrorEnabled(false);
                }
            }

            @Override
            public void afterTextChanged(Editable editable) {

            }
        });
        et_code.setOnFocusChangeListener(new View.OnFocusChangeListener() {
            @Override
            public void onFocusChange(View v, boolean hasFocus) {

                if (!hasFocus) {
                    if (!isValidEmail(et_code.getText())) {
//                        et_email.setError("Email is invalid");
//                        textInputLayout2.setError("Email is invalid");
                    } else {
//                        textInputLayout2.setError(null);
                    }
                }
            }
        });

    }

    public static boolean isValidEmail(CharSequence target) {
        return !TextUtils.isEmpty(target) && android.util.Patterns.EMAIL_ADDRESS.matcher(target).matches();
    }

//    介绍:
//    app:counterEnabled="true" //设置为true才能显字符数
//    app:counterMaxLength="5" //设置最大字符数为5
//    app:counterOverflowTextAppearance="@style/HintError" //设置超出字符数后提示文字的颜色,如果不设置默认为@color/colorAccent的颜色
//    android:layout_height="wrap_content">


}

四.登录样式4:

1.主函数代码:


import android.animation.AnimatorSet;
import android.animation.ObjectAnimator;
import android.content.Intent;
import android.view.View;
import android.view.animation.AccelerateDecelerateInterpolator;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.LinearLayout;

import androidx.annotation.Nullable;

import com.hjq.demo.R;
import com.hjq.demo.common.MyActivity;
import com.hjq.demo.helper.InputTextHelper;
import com.hjq.demo.other.IntentKey;
import com.hjq.demo.other.KeyboardWatcher;
import com.hjq.demo.wxapi.WXEntryActivity;
import com.hjq.image.ImageLoader;
import com.hjq.umeng.Platform;
import com.hjq.umeng.UmengClient;
import com.hjq.umeng.UmengLogin;

import butterknife.BindView;
import butterknife.OnClick;

/**
 *  登录界面
 */
public final class LoginActivity extends MyActivity
        implements UmengLogin.OnLoginListener,
        KeyboardWatcher.SoftKeyboardStateListener {

    @BindView(R.id.iv_login_logo)
    ImageView mLogoView;

    @BindView(R.id.ll_login_body)
    LinearLayout mBodyLayout;
    @BindView(R.id.et_login_phone)
    EditText mPhoneView;
    @BindView(R.id.et_login_password)
    EditText mPasswordView;

    @BindView(R.id.btn_login_commit)
    Button mCommitView;

    @BindView(R.id.v_login_blank)
    View mBlankView;

    @BindView(R.id.ll_login_other)
    View mOtherView;
    @BindView(R.id.iv_login_qq)
    View mQQView;
    @BindView(R.id.iv_login_wx)
    View mWeChatView;

    /** logo 缩放比例 */
    private final float mLogoScale = 0.8f;
    /** 动画时间 */
    private final int mAnimTime = 300;

    @Override
    protected int getLayoutId() {
        return R.layout.activity_login;
    }

    @Override
    protected void initView() {
        InputTextHelper.with(this)
                .addView(mPhoneView)
                .addView(mPasswordView)
                .setMain(mCommitView)
                .setListener(new InputTextHelper.OnInputTextListener() {

                    @Override
                    public boolean onInputChange(InputTextHelper helper) {
                        return mPhoneView.getText().toString().length() == 11 &&
                                mPasswordView.getText().toString().length() >= 6;
                    }
                })
                .build();

        post(new Runnable() {

            @Override
            public void run() {
                // 因为在小屏幕手机上面,因为计算规则的因素会导致动画效果特别夸张,所以不在小屏幕手机上面展示这个动画效果
                if (mBlankView.getHeight() > mBodyLayout.getHeight()) {
                    // 只有空白区域的高度大于登录框区域的高度才展示动画
                    KeyboardWatcher.with(LoginActivity.this)
                            .setListener(LoginActivity.this);
                }
            }
        });
    }

    @Override
    protected void initData() {
        // 判断用户当前有没有安装 QQ
        if (!UmengClient.isAppInstalled(this, Platform.QQ)) {
            mQQView.setVisibility(View.GONE);
        }

        // 判断用户当前有没有安装微信
        if (!UmengClient.isAppInstalled(this, Platform.WECHAT)) {
            mWeChatView.setVisibility(View.GONE);
        }

        // 如果这两个都没有安装就隐藏提示
        if (mQQView.getVisibility() == View.GONE && mWeChatView.getVisibility() == View.GONE) {
            mOtherView.setVisibility(View.GONE);
        }
    }

    @Override
    public void onRightClick(View v) {
        // 跳转到注册界面
        startActivityForResult(RegisterActivity.class, new ActivityCallback() {

            @Override
            public void onActivityResult(int resultCode, @Nullable Intent data) {
                // 如果已经注册成功,就执行登录操作
                if (resultCode == RESULT_OK && data != null) {
                    mPhoneView.setText(data.getStringExtra(IntentKey.PHONE));
                    mPasswordView.setText(data.getStringExtra(IntentKey.PASSWORD));
                    onClick(mCommitView);
                }
            }
        });
    }

    @OnClick({R.id.tv_login_forget, R.id.btn_login_commit, R.id.iv_login_qq, R.id.iv_login_wx})
    public void onClick(View v) {
        switch (v.getId()) {
            case R.id.tv_login_forget:
                startActivity(PasswordForgetActivity.class);
                break;
            case R.id.btn_login_commit:
                if (mPhoneView.getText().toString().length() != 11) {
                    toast(R.string.common_phone_input_error);
                } else {
                    showLoading();
                    postDelayed(new Runnable() {
                        @Override
                        public void run() {
                            showComplete();
                            // 处理登录
                            startActivityFinish(HomeActivity.class);
                        }
                    }, 2000);
                }
                break;
            case R.id.iv_login_qq:
            case R.id.iv_login_wx:
                toast("记得改好第三方 AppID 和 AppKey,否则会调不起来哦");
                Platform platform;
                switch (v.getId()) {
                    case R.id.iv_login_qq:
                        platform = Platform.QQ;
                        break;
                    case R.id.iv_login_wx:
                        platform = Platform.WECHAT;
                        toast("也别忘了改微信 " + WXEntryActivity.class.getSimpleName() + " 类所在的包名哦");
                        break;
                    default:
                        throw new IllegalStateException("are you ok?");
                }
                UmengClient.login(this, platform, this);
                break;
            default:
                break;
        }
    }

    @Override
    protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        // 友盟登录回调
        UmengClient.onActivityResult(this, requestCode, resultCode, data);
    }

    /**
     * 友盟第三方登录授权回调接口
     * {@link UmengLogin.OnLoginListener}
     */

    /**
     * 授权成功的回调
     *
     * @param platform      平台名称
     * @param data          用户资料返回
     */
    @Override
    public void onSucceed(Platform platform, UmengLogin.LoginData data) {
        // 判断第三方登录的平台
        switch (platform) {
            case QQ:
                break;
            case WECHAT:
                break;
            default:
                break;
        }

        ImageLoader.with(this)
                .load(data.getIcon())
                .circle()
                .into(mLogoView);

        toast("昵称:" + data.getName() + "\n" + "性别:" + data.getSex());
        toast("id:" + data.getId());
        toast("token:" + data.getToken());
    }

    /**
     * 授权失败的回调
     *
     * @param platform      平台名称
     * @param t             错误原因
     */
    @Override
    public void onError(Platform platform, Throwable t) {
        toast("第三方登录出错:" + t.getMessage());
    }

    /**
     * 授权取消的回调
     *
     * @param platform      平台名称
     */
    @Override
    public void onCancel(Platform platform) {
        toast("取消第三方登录");
    }

    /**
     * {@link KeyboardWatcher.SoftKeyboardStateListener}
     */

    @Override
    public void onSoftKeyboardOpened(int keyboardHeight) {
        int screenHeight = getResources().getDisplayMetrics().heightPixels;
        int[] location = new int[2];
        // 获取这个 View 在屏幕中的坐标(左上角)
        mBodyLayout.getLocationOnScreen(location);
        //int x = location[0];
        int y = location[1];
        int bottom = screenHeight - (y + mBodyLayout.getHeight());
        if (keyboardHeight > bottom){
            // 执行位移动画
            ObjectAnimator objectAnimator = ObjectAnimator.ofFloat(mBodyLayout, "translationY", 0, -(keyboardHeight - bottom));
            objectAnimator.setDuration(mAnimTime);
            objectAnimator.setInterpolator(new AccelerateDecelerateInterpolator());
            objectAnimator.start();

            // 执行缩小动画
            mLogoView.setPivotX(mLogoView.getWidth() / 2f);
            mLogoView.setPivotY(mLogoView.getHeight());
            AnimatorSet animatorSet = new AnimatorSet();
            ObjectAnimator scaleX = ObjectAnimator.ofFloat(mLogoView, "scaleX", 1.0f, mLogoScale);
            ObjectAnimator scaleY = ObjectAnimator.ofFloat(mLogoView, "scaleY", 1.0f, mLogoScale);
            ObjectAnimator translationY = ObjectAnimator.ofFloat(mLogoView, "translationY", 0.0f, -(keyboardHeight - bottom));
            animatorSet.play(translationY).with(scaleX).with(scaleY);
            animatorSet.setDuration(mAnimTime);
            animatorSet.start();
        }
    }

    @Override
    public void onSoftKeyboardClosed() {
        // 执行位移动画
        ObjectAnimator objectAnimator = ObjectAnimator.ofFloat(mBodyLayout, "translationY", mBodyLayout.getTranslationY(), 0);
        objectAnimator.setDuration(mAnimTime);
        objectAnimator.setInterpolator(new AccelerateDecelerateInterpolator());
        objectAnimator.start();

        if (mLogoView.getTranslationY() == 0){
            return;
        }
        // 执行放大动画
        mLogoView.setPivotX(mLogoView.getWidth() / 2f);
        mLogoView.setPivotY(mLogoView.getHeight());
        AnimatorSet animatorSet = new AnimatorSet();
        ObjectAnimator scaleX = ObjectAnimator.ofFloat(mLogoView, "scaleX", mLogoScale, 1.0f);
        ObjectAnimator scaleY = ObjectAnimator.ofFloat(mLogoView, "scaleY", mLogoScale, 1.0f);
        ObjectAnimator translationY = ObjectAnimator.ofFloat(mLogoView, "translationY", mLogoView.getTranslationY(), 0);
        animatorSet.play(translationY).with(scaleX).with(scaleY);
        animatorSet.setDuration(mAnimTime);
        animatorSet.start();
    }
}

 

package com.hjq.demo.other;

import android.app.Activity;
import android.app.Application;
import android.graphics.Rect;
import android.os.Build;
import android.os.Bundle;
import android.view.View;
import android.view.ViewTreeObserver;
import android.view.Window;
import android.view.WindowManager;

/**
  软键盘监听类
 */
public final class KeyboardWatcher implements
        ViewTreeObserver.OnGlobalLayoutListener,
        Application.ActivityLifecycleCallbacks {

    private Activity mActivity;
    private View mContentView;
    private SoftKeyboardStateListener mListeners;
    private boolean isSoftKeyboardOpened;
    private int mStatusBarHeight;

    public static KeyboardWatcher with(Activity activity) {
        return new KeyboardWatcher(activity);
    }

    private KeyboardWatcher(Activity activity) {
        mActivity = activity;
        mContentView = activity.findViewById(Window.ID_ANDROID_CONTENT);

        mActivity.getApplication().registerActivityLifecycleCallbacks(this);
        mContentView.getViewTreeObserver().addOnGlobalLayoutListener(this);

        // 获取 status_bar_height 资源的 ID
        int resourceId = mActivity.getResources().getIdentifier("status_bar_height", "dimen", "android");
        if (resourceId > 0) {
            //根据资源 ID 获取响应的尺寸值
            mStatusBarHeight = mActivity.getResources().getDimensionPixelSize(resourceId);
        }
    }

    /**
     * {@link ViewTreeObserver.OnGlobalLayoutListener}
     */

    @Override
    public void onGlobalLayout() {
        final Rect r = new Rect();
        //r will be populated with the coordinates of your view that area still visible.
        mContentView.getWindowVisibleDisplayFrame(r);

        final int heightDiff = mContentView.getRootView().getHeight() - (r.bottom - r.top);
        if (!isSoftKeyboardOpened && heightDiff > mContentView.getRootView().getHeight() / 4) {
            isSoftKeyboardOpened = true;
            if ((mActivity.getWindow().getAttributes().flags & WindowManager.LayoutParams.FLAG_FULLSCREEN) != WindowManager.LayoutParams.FLAG_FULLSCREEN) {
                if (mListeners != null) {
                    mListeners.onSoftKeyboardOpened(heightDiff - mStatusBarHeight);
                }
            } else {
                if (mListeners != null) {
                    mListeners.onSoftKeyboardOpened(heightDiff);
                }
            }

        } else if (isSoftKeyboardOpened && heightDiff < mContentView.getRootView().getHeight() / 4) {
            isSoftKeyboardOpened = false;
            if (mListeners != null) {
                mListeners.onSoftKeyboardClosed();
            }
        }
    }

    /**
     * 设置软键盘弹出监听
     */
    public void setListener(SoftKeyboardStateListener listener) {
        mListeners = listener;
    }

    /**
     * {@link Application.ActivityLifecycleCallbacks}
     */

    @Override
    public void onActivityCreated(Activity activity, Bundle savedInstanceState) {

    }

    @Override
    public void onActivityStarted(Activity activity) {

    }

    @Override
    public void onActivityResumed(Activity activity) {

    }

    @Override
    public void onActivityPaused(Activity activity) {

    }

    @Override
    public void onActivityStopped(Activity activity) {

    }

    @Override
    public void onActivitySaveInstanceState(Activity activity, Bundle outState) {

    }

    @Override
    public void onActivityDestroyed(Activity activity) {
        if (mActivity == activity) {
            mActivity.getApplication().unregisterActivityLifecycleCallbacks(this);
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
                mContentView.getViewTreeObserver().removeOnGlobalLayoutListener(this);
            }

            mActivity = null;
            mContentView = null;
            mListeners = null;
        }
    }

    /**
     * 软键盘状态监听器
     */
    public interface SoftKeyboardStateListener {

        /**
         * 软键盘弹出了
         * @param keyboardHeight            软键盘高度
         */
        void onSoftKeyboardOpened(int keyboardHeight);

        /**
         * 软键盘收起了
         */
        void onSoftKeyboardClosed();
    }
}

 

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="@color/white"
    android:gravity="center_horizontal"
    android:layoutAnimation="@anim/layout_animation_from_bottom"
    android:orientation="vertical"
    tools:context=".ui.activity.LoginActivity"
    tools:layoutAnimation="@null">

    <com.hjq.bar.TitleBar
        android:layout_width="match_parent"
        android:layout_height="50dp"
        app:backButton="false"
        app:barStyle="transparent"
        app:rightColor="@color/colorAccent"
        app:rightTitle="@string/login_register"
        app:title="" />

    <androidx.appcompat.widget.AppCompatImageView
        android:id="@+id/iv_login_logo"
        android:layout_width="120dp"
        android:layout_height="120dp"
        android:layout_marginTop="30dp"
        android:layout_marginBottom="30dp"
        android:src="@drawable/ic_logo" />

    <LinearLayout
        android:id="@+id/ll_login_body"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="vertical">

        <com.hjq.widget.view.ClearEditText
            android:id="@+id/et_login_phone"
            style="@style/EditTextStyle"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_marginLeft="40dp"
            android:layout_marginTop="10dp"
            android:layout_marginRight="40dp"
            android:hint="@string/common_phone_input_hint"
            android:inputType="textVisiblePassword"
            android:singleLine="true"
            app:regexType="mobile" />

        <View
            style="@style/HorizontalLineStyle"
            android:layout_marginLeft="40dp"
            android:layout_marginRight="40dp" />

        <com.hjq.widget.view.PasswordEditText
            android:id="@+id/et_login_password"
            style="@style/EditTextStyle"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_marginLeft="40dp"
            android:layout_marginTop="20dp"
            android:layout_marginRight="40dp"
            android:hint="@string/common_password_input_error"
            android:maxLength="20"
            android:maxLines="1" />

        <View
            style="@style/HorizontalLineStyle"
            android:layout_marginLeft="40dp"
            android:layout_marginRight="40dp" />

        <androidx.appcompat.widget.AppCompatTextView
            android:id="@+id/tv_login_forget"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="right"
            android:layout_marginLeft="40dp"
            android:layout_marginTop="15dp"
            android:layout_marginRight="60dp"
            android:text="@string/login_forget"
            android:textColor="@color/colorAccent" />

        <androidx.appcompat.widget.AppCompatButton
            android:id="@+id/btn_login_commit"
            style="@style/ButtonStyle"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_marginLeft="40dp"
            android:layout_marginTop="30dp"
            android:layout_marginRight="40dp"
            android:text="@string/login_text" />

    </LinearLayout>

    <View
        android:id="@+id/v_login_blank"
        android:layout_width="wrap_content"
        android:layout_height="0px"
        android:layout_weight="5" />

    <LinearLayout
        android:id="@+id/ll_login_other"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center_horizontal"
        android:gravity="center_vertical"
        android:orientation="horizontal">

        <View
            style="@style/HorizontalLineStyle"
            android:layout_width="60dp"
            android:layout_weight="1" />

        <androidx.appcompat.widget.AppCompatTextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_marginLeft="15dp"
            android:layout_marginRight="15dp"
            android:text="@string/login_other"
            android:textColor="@color/black50" />

        <View
            style="@style/HorizontalLineStyle"
            android:layout_width="60dp"
            android:layout_weight="1" />
    </LinearLayout>

    <LinearLayout
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:orientation="horizontal">

        <com.hjq.widget.view.ScaleImageView
            android:id="@+id/iv_login_qq"
            android:layout_width="35dp"
            android:layout_height="35dp"
            android:layout_marginStart="30dp"
            android:layout_marginTop="25dp"
            android:layout_marginEnd="30dp"
            android:layout_marginBottom="25dp"
            android:layout_weight="1"
            android:src="@drawable/ic_login_qq"
            app:scaleRatio="1.2" />

        <com.hjq.widget.view.ScaleImageView
            android:id="@+id/iv_login_wx"
            android:layout_width="35dp"
            android:layout_height="35dp"
            android:layout_marginStart="30dp"
            android:layout_marginTop="25dp"
            android:layout_marginEnd="30dp"
            android:layout_marginBottom="25dp"
            android:layout_weight="1"
            android:src="@drawable/ic_login_wx"
            app:scaleRatio="1.2" />
    </LinearLayout>

</LinearLayout>

layout_animation_from_bottom.xml 

<?xml version="1.0" encoding="utf-8"?>
<layoutAnimation xmlns:android="http://schemas.android.com/apk/res/android"
    android:animation="@anim/item_animation_from_bottom"
    android:animationOrder="normal"
    android:delay="15%" />
 <!-- 默认文本框样式 -->
    <style name="EditTextStyle">
        <item name="android:background">@null</item>
        <item name="android:textSize">15sp</item>
        <item name="android:textColorHint">#A4A4A4</item>
        <item name="android:textColor">#333333</item>
        <item name="android:paddingTop">10dp</item>
        <item name="android:paddingBottom">10dp</item>
        <item name="android:paddingLeft">10dp</item>
        <item name="android:paddingRight">10dp</item>
    </style>
 <!-- 默认水平分割线样式 -->
    <style name="HorizontalLineStyle">
        <item name="android:layout_width">match_parent</item>
        <item name="android:layout_height">@dimen/line_size</item>
        <item name="android:background">@color/colorLine</item>
    </style>

 

 <!-- 默认圆角按钮样式 -->
    <style name="ButtonStyle" parent="Widget.AppCompat.Button.Borderless">
        <item name="android:paddingLeft">15dp</item>
        <item name="android:paddingRight">15dp</item>
        <item name="android:paddingTop">8dp</item>
        <item name="android:paddingBottom">8dp</item>
        <item name="android:textSize">14sp</item>
        <item name="android:textColor">@color/white90</item>
        <item name="android:gravity">center</item>
        <item name="android:background">@drawable/selector_button</item>
        <item name="android:foreground">@null</item>
    </style>

 selector_button.xml

<?xml version="1.0" encoding="utf-8"?>
<!-- 默认圆角按钮样式 -->
<selector xmlns:android="http://schemas.android.com/apk/res/android">

    <!-- 禁用状态 -->
    <item android:state_enabled="false">
        <shape android:shape="rectangle">
            <corners android:radius="@dimen/button_round_size" />
            <solid android:color="@color/colorButtonDisable" />
        </shape>
    </item>

    <!-- 按压状态 -->
    <item android:state_pressed="true">
        <shape android:shape="rectangle">
            <corners android:radius="@dimen/button_round_size" />
            <solid android:color="@color/colorButtonPressed" />
        </shape>
    </item>

    <!-- 焦点状态 -->
    <item android:state_focused="true">
        <shape android:shape="rectangle">
            <corners android:radius="@dimen/button_round_size" />
            <solid android:color="@color/colorButtonPressed" />
        </shape>
    </item>

    <!-- 默认状态 -->
    <item>
        <shape android:shape="rectangle">
            <corners android:radius="@dimen/button_round_size" />
            <solid android:color="@color/colorAccent" />
        </shape>
    </item>

</selector>

 五.登录之重置密码:

1.主函数代码:

import android.view.View;
import android.widget.Button;
import android.widget.EditText;

import com.hjq.demo.R;
import com.hjq.demo.common.MyActivity;
import com.hjq.demo.helper.InputTextHelper;

import butterknife.BindView;
import butterknife.OnClick;

/**
 *  重置密码
 */
public final class PasswordResetActivity extends MyActivity {

    @BindView(R.id.et_password_reset_password1)
    EditText mPasswordView1;
    @BindView(R.id.et_password_reset_password2)
    EditText mPasswordView2;
    @BindView(R.id.btn_password_reset_commit)
    Button mCommitView;

    @Override
    protected int getLayoutId() {
        return R.layout.activity_password_reset;
    }

    @Override
    protected void initView() {
        InputTextHelper.with(this)
                .addView(mPasswordView1)
                .addView(mPasswordView2)
                .setMain(mCommitView)
                .setListener(new InputTextHelper.OnInputTextListener() {

                    @Override
                    public boolean onInputChange(InputTextHelper helper) {
                        return mPasswordView1.getText().toString().length() >= 6 &&
                                mPasswordView1.getText().toString().equals(mPasswordView2.getText().toString());
                    }
                })
                .build();
    }

    @Override
    protected void initData() {

    }

    @OnClick({R.id.btn_password_reset_commit})
    public void onClick(View v) {
        switch (v.getId()) {
            case R.id.btn_password_reset_commit:
                toast(R.string.password_reset_success);
                finish();
                break;
            default:
                break;
        }
    }
}

2.布局:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".ui.activity.PasswordResetActivity">

    <com.hjq.bar.TitleBar
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:title="@string/password_reset_title" />

    <com.hjq.widget.view.PasswordEditText
        android:id="@+id/et_password_reset_password1"
        style="@style/EditTextStyle"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_marginTop="15dp"
        android:background="@color/white"
        android:drawableLeft="@drawable/ic_small_safe"
        android:drawablePadding="15dp"
        android:hint="@string/password_reset_phone_hint1"
        android:inputType="textPassword"
        android:maxLength="20"
        android:maxLines="1"
        android:paddingLeft="20dp"
        android:paddingTop="18dp"
        android:paddingRight="20dp"
        android:paddingBottom="18dp" />

    <View
        style="@style/HorizontalLineStyle"
        android:layout_marginLeft="20dp"
        android:layout_marginRight="20dp" />

    <com.hjq.widget.view.PasswordEditText
        android:id="@+id/et_password_reset_password2"
        style="@style/EditTextStyle"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@color/white"
        android:drawableLeft="@drawable/ic_small_safe"
        android:drawablePadding="15dp"
        android:hint="@string/password_reset_phone_hint2"
        android:maxLength="20"
        android:maxLines="1"
        android:paddingLeft="20dp"
        android:paddingTop="18dp"
        android:paddingRight="20dp"
        android:paddingBottom="18dp" />

    <androidx.appcompat.widget.AppCompatButton
        android:id="@+id/btn_password_reset_commit"
        style="@style/ButtonStyle"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_marginLeft="40dp"
        android:layout_marginTop="40dp"
        android:layout_marginRight="40dp"
        android:text="@string/common_step_complete" />

</LinearLayout>

 

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="@color/white"
    android:orientation="vertical"
    tools:context=".ui.activity.RegisterActivity">

    <com.hjq.bar.TitleBar
        android:layout_width="match_parent"
        android:layout_height="50dp"
        app:backButton="false"
        app:barStyle="transparent"
        app:leftColor="@color/colorAccent"
        app:leftTitle="@string/register_login"
        app:title="" />

    <androidx.core.widget.NestedScrollView
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:layout_marginLeft="40dp"
            android:layout_marginRight="40dp"
            android:gravity="center_horizontal"
            android:layoutAnimation="@anim/layout_animation_fall_down"
            android:orientation="vertical"
            tools:layoutAnimation="@null">

            <androidx.appcompat.widget.AppCompatTextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginTop="20dp"
                android:text="@string/register_title"
                android:textColor="@color/black60"
                android:textSize="23sp" />

            <androidx.appcompat.widget.AppCompatTextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginTop="20dp"
                android:text="@string/register_hint"
                android:textColor="@color/black20"
                android:textSize="14sp" />

            <LinearLayout
                android:id="@+id/ll_register_edit1"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginTop="30dp"
                android:gravity="center_vertical"
                android:orientation="horizontal">

                <FrameLayout
                    android:layout_width="0px"
                    android:layout_height="wrap_content"
                    android:layout_weight="1">

                    <com.hjq.widget.view.RegexEditText
                        android:id="@+id/et_register_phone"
                        style="@style/EditTextStyle"
                        android:layout_width="match_parent"
                        android:layout_height="wrap_content"
                        android:hint="@string/common_phone_input_hint"
                        android:inputType="textVisiblePassword"
                        android:maxLines="1"
                        android:singleLine="true"
                        app:regexType="mobile" />

                    <View
                        style="@style/HorizontalLineStyle"
                        android:layout_gravity="bottom" />
                </FrameLayout>

                <com.hjq.widget.view.CountdownView
                    android:id="@+id/cv_register_countdown"
                    style="@style/CountdownViewStyle" />
            </LinearLayout>

            <androidx.appcompat.widget.AppCompatEditText
                android:id="@+id/et_register_code"
                style="@style/EditTextStyle"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginTop="20dp"
                android:hint="@string/common_code_input_hint"
                android:inputType="number"
                android:maxLength="4"
                android:maxLines="1"
                android:singleLine="true" />

            <View style="@style/HorizontalLineStyle" />

            <com.hjq.widget.view.PasswordEditText
                android:id="@+id/et_register_password1"
                style="@style/EditTextStyle"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginTop="20dp"
                android:hint="@string/register_password_hint1"
                android:maxLength="20"
                android:maxLines="1" />

            <View style="@style/HorizontalLineStyle" />

            <com.hjq.widget.view.PasswordEditText
                android:id="@+id/et_register_password2"
                style="@style/EditTextStyle"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginTop="20dp"
                android:hint="@string/register_password_hint2"
                android:maxLength="20"
                android:maxLines="1" />

            <View style="@style/HorizontalLineStyle" />

            <androidx.appcompat.widget.AppCompatButton
                android:id="@+id/btn_register_commit"
                style="@style/ButtonStyle"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginTop="30dp"
                android:layout_marginBottom="20dp"
                android:text="@string/register_title" />

        </LinearLayout>

    </androidx.core.widget.NestedScrollView>

</LinearLayout>
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".ui.activity.PasswordForgetActivity">

    <com.hjq.bar.TitleBar
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:title="@string/password_forget_title" />

    <com.hjq.widget.view.RegexEditText
        android:id="@+id/et_password_forget_phone"
        style="@style/EditTextStyle"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_marginTop="15dp"
        android:background="@color/white"
        android:drawableLeft="@drawable/ic_small_phone"
        android:drawablePadding="15dp"
        android:hint="@string/common_phone_input_hint"
        android:inputType="textVisiblePassword"
        android:paddingLeft="20dp"
        android:paddingTop="18dp"
        android:paddingRight="20dp"
        android:paddingBottom="18dp"
        android:singleLine="true"
        app:regexType="mobile" />

    <View
        style="@style/HorizontalLineStyle"
        android:layout_marginLeft="20dp"
        android:layout_marginRight="20dp" />

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@color/white"
        android:orientation="horizontal">

        <androidx.appcompat.widget.AppCompatEditText
            android:id="@+id/et_password_forget_code"
            style="@style/EditTextStyle"
            android:layout_width="0px"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:background="@color/white"
            android:drawableLeft="@drawable/ic_small_safe"
            android:drawablePadding="15dp"
            android:hint="@string/common_code_input_hint"
            android:paddingLeft="20dp"
            android:paddingTop="18dp"
            android:paddingRight="20dp"
            android:paddingBottom="18dp"
            android:singleLine="true" />

        <com.hjq.widget.view.CountdownView
            android:id="@+id/cv_password_forget_countdown"
            style="@style/CountdownViewStyle" />

    </LinearLayout>

    <androidx.appcompat.widget.AppCompatButton
        android:id="@+id/btn_password_forget_commit"
        style="@style/ButtonStyle"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_marginLeft="40dp"
        android:layout_marginTop="50dp"
        android:layout_marginRight="40dp"
        android:text="@string/common_step_next" />

</LinearLayout>

 

https://github.com/qingmei2/Samples-Android

 请忽略下面的笔记:

/**
 * 自定义绚丽的ProgressBar.
 */
public class ProgressBarView1 extends View {
    /**
     * 进度条所占用的角度
     */
    private static final int ARC_FULL_DEGREE = 300;
    /**
     * 弧线的宽度
     */
    private int STROKE_WIDTH;
 
 
    /**
     * 组件的宽,高
     */
    private int width, height;
    /**
     * 进度条最大值和当前进度值
     */
    private float max, progress;
 
 
    /**
     * 是否允许拖动进度条
     */
    private boolean draggingEnabled = false;
 
 
    /**
     * 绘制弧线的矩形区域
     */
    private RectF circleRectF;
 
 
    /**
     * 绘制弧线的画笔
     */
    private Paint progressPaint;
    /**
     * 绘制文字的画笔
     */
    private Paint textPaint;
    /**
     * 绘制当前进度值的画笔
     */
    private Paint thumbPaint;
 
 
    /**
     * 圆弧的半径
     */
    private int circleRadius;
    /**
     * 圆弧圆心位置
     */
    private int centerX, centerY;
 
 
    public ProgressBarView1(Context context) {
        super(context);
        init();
    }
 
 
    public ProgressBarView1(Context context, AttributeSet attrs) {
        super(context, attrs);
        init();
    }
 
 
    public ProgressBarView1(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init();
    }
 
 
    private void init() {
        progressPaint = new Paint();
        progressPaint.setAntiAlias(true);
 
 
        textPaint = new Paint();
        textPaint.setColor(Color.WHITE);
        textPaint.setAntiAlias(true);
 
 
        thumbPaint = new Paint();
        thumbPaint.setAntiAlias(true);
 
 
        //使用自定义字体
        textPaint.setTypeface(Typeface.createFromAsset(getContext().getAssets(), "fangz.ttf"));
    }
 
 
    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
 
 
        if (width == 0 || height == 0) {
            width = getWidth();
            height = getHeight();
 
 
            //计算圆弧半径和圆心点
            circleRadius = Math.min(width, height) / 2;
            STROKE_WIDTH = circleRadius / 12;
            circleRadius -= STROKE_WIDTH;
 
 
            centerX = width / 2;
            centerY = height / 2;
 
 
            //圆弧所在矩形区域
            circleRectF = new RectF();
            circleRectF.left = centerX - circleRadius;
            circleRectF.top = centerY - circleRadius;
            circleRectF.right = centerX + circleRadius;
            circleRectF.bottom = centerY + circleRadius;
        }
    }
 
 
    private Rect textBounds = new Rect();
 
 
    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
 
 
        float start = 90 + ((360 - ARC_FULL_DEGREE) >> 1); //进度条起始点
        float sweep1 = ARC_FULL_DEGREE * (progress / max); //进度划过的角度
        float sweep2 = ARC_FULL_DEGREE - sweep1; //剩余的角度
 
 
        //绘制起始位置小圆形
        progressPaint.setColor(Color.WHITE);
        progressPaint.setStrokeWidth(0);
        progressPaint.setStyle(Paint.Style.FILL);
        float radians = (float) (((360.0f - ARC_FULL_DEGREE) / 2) / 180 * Math.PI);
        float startX = centerX - circleRadius * (float) Math.sin(radians);
        float startY = centerY + circleRadius * (float) Math.cos(radians);
        canvas.drawCircle(startX, startY, STROKE_WIDTH / 2, progressPaint);
 
 
        //绘制进度条
        progressPaint.setStrokeWidth(STROKE_WIDTH);
        progressPaint.setStyle(Paint.Style.STROKE);//设置空心
        canvas.drawArc(circleRectF, start, sweep1, false, progressPaint);
        //绘制进度条背景
        progressPaint.setColor(Color.parseColor("#d64444"));
        canvas.drawArc(circleRectF, start + sweep1, sweep2, false, progressPaint);
 
 
        //绘制结束位置小圆形
        progressPaint.setStrokeWidth(0);
        progressPaint.setStyle(Paint.Style.FILL);
        float endX = centerX + circleRadius * (float) Math.sin(radians);
        float endY = centerY + circleRadius * (float) Math.cos(radians);
        canvas.drawCircle(endX, endY, STROKE_WIDTH / 2, progressPaint);
 
 
        //上一行文字
        textPaint.setTextSize(circleRadius >> 1);
        String text = (int) (100 * progress / max) + "";
        float textLen = textPaint.measureText(text);
        //计算文字高度
        textPaint.getTextBounds("8", 0, 1, textBounds);
        float h1 = textBounds.height();
        //% 前面的数字水平居中,适当调整
        float extra = text.startsWith("1") ? -textPaint.measureText("1") / 2 : 0;
        canvas.drawText(text, centerX - textLen / 2 + extra, centerY - 30 + h1 / 2, textPaint);
 
 
        //百分号
        textPaint.setTextSize(circleRadius >> 2);
        canvas.drawText("%", centerX + textLen / 2 + extra + 5, centerY - 30 + h1 / 2, textPaint);
 
 
        //下一行文字
        textPaint.setTextSize(circleRadius / 5);
        text = "可用内存充足";
        textLen = textPaint.measureText(text);
        textPaint.getTextBounds(text, 0, text.length(), textBounds);
        float h2 = textBounds.height();
        canvas.drawText(text, centerX - textLen / 2, centerY + h1 / 2 + h2, textPaint);
 
 
        //绘制进度位置,也可以直接替换成一张图片
        float progressRadians = (float) (((360.0f - ARC_FULL_DEGREE) / 2 + sweep1) / 180 * Math.PI);
        float thumbX = centerX - circleRadius * (float) Math.sin(progressRadians);
        float thumbY = centerY + circleRadius * (float) Math.cos(progressRadians);
        thumbPaint.setColor(Color.parseColor("#33d64444"));
        canvas.drawCircle(thumbX, thumbY, STROKE_WIDTH * 2.0f, thumbPaint);
        thumbPaint.setColor(Color.parseColor("#99d64444"));
        canvas.drawCircle(thumbX, thumbY, STROKE_WIDTH * 1.4f, thumbPaint);
        thumbPaint.setColor(Color.WHITE);
        canvas.drawCircle(thumbX, thumbY, STROKE_WIDTH * 0.8f, thumbPaint);
    }
 
 
    private boolean isDragging = false;
 
 
    @Override
    public boolean onTouchEvent(@NonNull MotionEvent event) {
        if (!draggingEnabled) {
            return super.onTouchEvent(event);
        }
 
 
        //处理拖动事件
        float currentX = event.getX();
        float currentY = event.getY();
 
 
        int action = event.getAction();
        switch (action) {
            case MotionEvent.ACTION_DOWN:
                //判断是否在进度条thumb位置
                if (checkOnArc(currentX, currentY)) {
                    float newProgress = calDegreeByPosition(currentX, currentY) / ARC_FULL_DEGREE * max;
                    setProgressSync(newProgress);
                    isDragging = true;
                }
                break;
 
 
            case MotionEvent.ACTION_MOVE:
                if (isDragging) {
                    //判断拖动时是否移出去了
                    if (checkOnArc(currentX, currentY)) {
                        setProgressSync(calDegreeByPosition(currentX, currentY) / ARC_FULL_DEGREE * max);
                    } else {
                        isDragging = false;
                    }
                }
                break;
 
 
            case MotionEvent.ACTION_UP:
                isDragging = false;
                break;
        }
 
 
        return true;
    }
 
 
    private float calDistance(float x1, float y1, float x2, float y2) {
        return (float) Math.sqrt((x1 - x2) * (x1 - x2) + (y1 - y2) * (y1 - y2));
    }
 
 
    /**
     * 判断该点是否在弧线上(附近)
     */
    private boolean checkOnArc(float currentX, float currentY) {
        float distance = calDistance(currentX, currentY, centerX, centerY);
        float degree = calDegreeByPosition(currentX, currentY);
        return distance > circleRadius - STROKE_WIDTH * 5 && distance < circleRadius + STROKE_WIDTH * 5
                && (degree >= -8 && degree <= ARC_FULL_DEGREE + 8);
    }
 
 
    /**
     * 根据当前位置,计算出进度条已经转过的角度。
     */
    private float calDegreeByPosition(float currentX, float currentY) {
        float a1 = (float) (Math.atan(1.0f * (centerX - currentX) / (currentY - centerY)) / Math.PI * 180);
        if (currentY < centerY) {
            a1 += 180;
        } else if (currentY > centerY && currentX > centerX) {
            a1 += 360;
        }
 
 
        return a1 - (360 - ARC_FULL_DEGREE) / 2;
    }
 
 
    public void setMax(int max) {
        this.max = max;
        invalidate();
    }
 
 
    public void setProgress(float progress) {
        final float validProgress = checkProgress(progress);
        //动画切换进度值
        new Thread(new Runnable() {
            @Override
            public void run() {
                float oldProgress = ProgressBarView1.this.progress;
                for (int i = 1; i <= 100; i++) {
                    ProgressBarView1.this.progress = oldProgress + (validProgress - oldProgress) * (1.0f * i / 100);
                    postInvalidate();
                    SystemClock.sleep(20);
                }
            }
        }).start();
    }
 
 
    public void setProgressSync(float progress) {
        this.progress = checkProgress(progress);
        invalidate();
    }
 
 
    //保证progress的值位于[0,max]
    private float checkProgress(float progress) {
        if (progress < 0) {
            return 0;
        }
 
 
        return progress > max ? max : progress;
    }
 
 
    public void setDraggingEnabled(boolean draggingEnabled) {
        this.draggingEnabled = draggingEnabled;
    }
}

 

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值